per type xp cost

This commit is contained in:
alexcrea 2026-05-23 18:04:46 +02:00
parent b18cf1fd59
commit d67380da1a
Signed by: alexcrea
GPG key ID: E346CD16413450E3
8 changed files with 150 additions and 79 deletions

View file

@ -7,6 +7,7 @@ import org.bukkit.inventory.ItemStack;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import xyz.alexcrea.cuanvil.util.AnvilUseType;
import xyz.alexcrea.cuanvil.util.AnvilXpUtil.AnvilCost;
/**
* Called after custom anvil processed the click on the result on the anvil inventory.
@ -40,13 +41,13 @@ public class CATreatAnvilResultEvent extends Event {
@Nullable
private ItemStack result;
private int levelCost;
private final AnvilCost cost;
public CATreatAnvilResultEvent(@NotNull PrepareAnvilEvent event, AnvilUseType useType, @Nullable ItemStack result, int levelCost) {
public CATreatAnvilResultEvent(@NotNull PrepareAnvilEvent event, AnvilUseType useType, @Nullable ItemStack result, AnvilCost cost) {
this.event = event;
this.useType = useType;
this.result = result;
this.levelCost = levelCost;
this.cost = cost;
}
/**
@ -103,10 +104,12 @@ public class CATreatAnvilResultEvent extends Event {
* <li>Item rename</li>
* </ul>
*
* @deprecated use #{@link #getCost()} instead
* @return The current cost.
*/
@Deprecated(forRemoval = true, since = "1.17.0")
public int getLevelCost() {
return levelCost;
return cost.sum();
}
/**
@ -123,9 +126,33 @@ public class CATreatAnvilResultEvent extends Event {
* <li>Item rename</li>
* </ul>
*
* @deprecated use #{@link #getCost()} and set value on this instead
* @param levelCost The new cost.
*/
@Deprecated(forRemoval = true, since = "1.17.0")
public void setLevelCost(int levelCost) {
this.levelCost = levelCost;
cost.setGeneric(levelCost - cost.getGeneric() - cost.sum());
}
/**
* Allow access to the current cost of the event
* Note that modifying this object will change the event resulting cost
*
* <h3>Important note:</h3>
* the final price are re calculated on click for the following use case:
* <ul>
* <li>Custom craft</li>
* <li>Unit repair</li>
* <li>Lore edit</li>
* </ul>
* This value will be used as final price for:
* <li>Item merge</li>
* <li>Item rename</li>
*
* @return the current anvil cost
*/
public AnvilCost getCost() {
return cost;
}
}

View file

@ -30,6 +30,7 @@ import xyz.alexcrea.cuanvil.dependency.util.PlatformUtil
import xyz.alexcrea.cuanvil.dependency.util.PlatformUtil.componentLore
import xyz.alexcrea.cuanvil.listener.PrepareAnvilListener.Companion.ANVIL_OUTPUT_SLOT
import xyz.alexcrea.cuanvil.util.AnvilUseType
import xyz.alexcrea.cuanvil.util.AnvilXpUtil
import xyz.alexcrea.cuanvil.util.MetricsUtil.trackError
import java.util.logging.Level
@ -235,12 +236,12 @@ object DependencyManager {
event: PrepareAnvilEvent,
result: ItemStack,
useType: AnvilUseType,
cost: Int
cost: AnvilXpUtil.AnvilCost
): CATreatAnvilResultEvent? {
val treatEvent = CATreatAnvilResultEvent(event, useType, result, cost)
try {
unsafeTryTreatAnvilResult(treatEvent)
return treatEvent;
return treatEvent
} catch (e: Exception) {
logExceptionAndClear(event.view.player, event.inventory, e)
return null

View file

@ -16,6 +16,7 @@ import org.bukkit.inventory.AnvilInventory
import org.bukkit.inventory.ItemStack
import xyz.alexcrea.cuanvil.listener.PrepareAnvilListener
import xyz.alexcrea.cuanvil.util.AnvilXpUtil
import xyz.alexcrea.cuanvil.util.AnvilXpUtil.AnvilCost
import xyz.alexcrea.cuanvil.util.MetricsUtil.trackError
import java.util.logging.Level
import kotlin.reflect.KClass
@ -58,14 +59,14 @@ class DisenchantmentDependency {
DisenchantEvent.onEvent(event)
if (event.result != null) {
CustomAnvil.log("Detected pre anvil item extract bypass.")
AnvilXpUtil.setAnvilInvXp(event.inventory, event.view, player, event.inventory.repairCost)
AnvilXpUtil.setAnvilInvCost(event.inventory, event.view, player, AnvilCost(event.inventory.repairCost))
return true
}
ShatterEvent.onEvent(event)
if (event.result != null) {
CustomAnvil.log("Detected pre anvil split enchant bypass.")
AnvilXpUtil.setAnvilInvXp(event.inventory, event.view, player, event.inventory.repairCost)
AnvilXpUtil.setAnvilInvCost(event.inventory, event.view, player, AnvilCost(event.inventory.repairCost))
return true
}

View file

@ -11,6 +11,7 @@ import valorless.havenbags.features.BagSkin
import valorless.havenbags.features.BagUpgrade
import xyz.alexcrea.cuanvil.listener.PrepareAnvilListener
import xyz.alexcrea.cuanvil.util.AnvilXpUtil
import xyz.alexcrea.cuanvil.util.AnvilXpUtil.AnvilCost
class HavenBagsDependency {
@ -53,14 +54,14 @@ class HavenBagsDependency {
bagSkin.onPrepareAnvil(event)
if (event.result != null) {
CustomAnvil.log("Detected pre anvil heaven bag anvil skin.")
AnvilXpUtil.setAnvilInvXp(event.inventory, event.view, player, event.inventory.repairCost)
AnvilXpUtil.setAnvilInvCost(event.inventory, event.view, player, AnvilCost(event.inventory.repairCost))
return true
}
bagUpgrade.onPrepareAnvil(event)
if (event.result != null) {
CustomAnvil.log("Detected pre anvil heaven bag anvil upgrade.")
AnvilXpUtil.setAnvilInvXp(event.inventory, event.view, player, event.inventory.repairCost)
AnvilXpUtil.setAnvilInvCost(event.inventory, event.view, player, AnvilCost(event.inventory.repairCost))
return true
}

View file

@ -25,6 +25,7 @@ import xyz.alexcrea.cuanvil.recipe.AnvilCustomRecipe
import xyz.alexcrea.cuanvil.util.AnvilLoreEditUtil
import xyz.alexcrea.cuanvil.util.AnvilUseType
import xyz.alexcrea.cuanvil.util.AnvilXpUtil
import xyz.alexcrea.cuanvil.util.AnvilXpUtil.AnvilCost
import xyz.alexcrea.cuanvil.util.CustomRecipeUtil
import xyz.alexcrea.cuanvil.util.MiniMessageUtil
import xyz.alexcrea.cuanvil.util.UnitRepairUtil.getRepair
@ -350,13 +351,13 @@ class AnvilResultListener : Listener {
}
private fun getFromLoreEditXpCost(
xpCost: AtomicInteger,
cost: AnvilCost,
player: Player,
inventory: AnvilInventory,
): Int {
if (GameMode.CREATIVE == player.gameMode) return 0
val repairCost = xpCost.get()
val repairCost = cost.sum()
return if ((inventory.maximumRepairCost <= repairCost)
|| (player.level < repairCost)
) Int.MIN_VALUE
@ -376,9 +377,9 @@ class AnvilResultListener : Listener {
val editType = AnvilLoreEditUtil.bookLoreEditIsAppend(leftItem, rightItem) ?: return false
val xpCost = AtomicInteger()
val cost = AnvilCost()
if (editType) {
if (output != AnvilLoreEditUtil.handleLoreAppendByBook(player, leftItem, bookMeta, xpCost)) return false
if (output != AnvilLoreEditUtil.handleLoreAppendByBook(player, leftItem, bookMeta, cost)) return false
// Remove pages to book
val clearedBook: ItemStack?
@ -394,10 +395,10 @@ class AnvilResultListener : Listener {
event, player, inventory,
null, 0,
clearedBook, 0,
output, getFromLoreEditXpCost(xpCost, player, inventory)
output, getFromLoreEditXpCost(cost, player, inventory)
)
} else {
if (output != AnvilLoreEditUtil.handleLoreRemoveByBook(player, leftItem, xpCost)) return false
if (output != AnvilLoreEditUtil.handleLoreRemoveByBook(player, leftItem, cost)) return false
// fill book meta
val lore = DependencyManager.stripLore(leftItem)
@ -430,7 +431,7 @@ class AnvilResultListener : Listener {
event, player, inventory,
null, 0,
rightCopy, 0,
output, getFromLoreEditXpCost(xpCost, player, inventory)
output, getFromLoreEditXpCost(cost, player, inventory)
)
}
}
@ -448,9 +449,9 @@ class AnvilResultListener : Listener {
val editTypeIsAppend = AnvilLoreEditUtil.paperLoreEditIsAppend(leftItem, rightItem) ?: return false
val xpCost = AtomicInteger()
val cost = AnvilCost()
if (editTypeIsAppend) {
if (output != AnvilLoreEditUtil.handleLoreAppendByPaper(player, leftItem, rightItem, xpCost)) return false
if (output != AnvilLoreEditUtil.handleLoreAppendByPaper(player, leftItem, rightItem, cost)) return false
val paperCopy: ItemStack?
if (LoreEditType.APPEND_PAPER.doConsume) {
@ -468,18 +469,18 @@ class AnvilResultListener : Listener {
event, player, inventory,
paperCopy, 0,
rightItem, 1,
output, getFromLoreEditXpCost(xpCost, player, inventory)
output, getFromLoreEditXpCost(cost, player, inventory)
)
} else {
extractAnvilResult(
event, player, inventory,
null, 0,
paperCopy, 0,
output, getFromLoreEditXpCost(xpCost, player, inventory)
output, getFromLoreEditXpCost(cost, player, inventory)
)
}
} else {
if (output != AnvilLoreEditUtil.handleLoreRemoveByPaper(player, leftItem, xpCost)) return false
if (output != AnvilLoreEditUtil.handleLoreRemoveByPaper(player, leftItem, cost)) return false
val leftMeta = leftItem.itemMeta
if (leftMeta == null || !leftMeta.hasLore()) return false
@ -512,14 +513,14 @@ class AnvilResultListener : Listener {
event, player, inventory,
rightClone, 0,
rightItem, 1,
output, getFromLoreEditXpCost(xpCost, player, inventory)
output, getFromLoreEditXpCost(cost, player, inventory)
)
} else {
extractAnvilResult(
event, player, inventory,
null, 0,
rightClone, 0,
output, getFromLoreEditXpCost(xpCost, player, inventory)
output, getFromLoreEditXpCost(cost, player, inventory)
)
}
}

View file

@ -26,10 +26,10 @@ import xyz.alexcrea.cuanvil.dependency.DependencyManager
import xyz.alexcrea.cuanvil.dialog.AnvilRenameDialog
import xyz.alexcrea.cuanvil.enchant.CAEnchantment
import xyz.alexcrea.cuanvil.util.*
import xyz.alexcrea.cuanvil.util.AnvilXpUtil.AnvilCost
import xyz.alexcrea.cuanvil.util.MaterialUtil.isAir
import xyz.alexcrea.cuanvil.util.UnitRepairUtil.getRepair
import xyz.alexcrea.cuanvil.util.dialog.AnvilRenameDialogUtil
import java.util.concurrent.atomic.AtomicInteger
/**
* Listener for anvil events
@ -60,7 +60,7 @@ class PrepareAnvilListener : Listener {
// Test if custom anvil is bypassed before immutability test
if (DependencyManager.earlyTryEventPreAnvilBypass(event, player)) {
// even if we got bypassed we still want to set price
AnvilXpUtil.setAnvilInvXp(inventory, event.view, player, event.inventory.repairCost)
AnvilXpUtil.setAnvilInvCost(inventory, event.view, player, AnvilCost(event.inventory.repairCost))
return
}
@ -90,7 +90,7 @@ class PrepareAnvilListener : Listener {
// Test if the event should bypass custom anvil.
if (DependencyManager.tryEventPreAnvilBypass(event, player)) {
// even if we got bypassed we still want to set price
AnvilXpUtil.setAnvilInvXp(inventory, event.view, player, event.inventory.repairCost)
AnvilXpUtil.setAnvilInvCost(inventory, event.view, player, AnvilCost(event.inventory.repairCost))
return
}
@ -198,17 +198,17 @@ class PrepareAnvilListener : Listener {
// Maybe add an option on custom craft to ignore/not ignore penalty ??
val xpCost = recipe.determineCost(amount, first, resultItem)
val levelCost =
if (recipe.removeExactLinearXp) AnvilXpUtil.calculateMinimumLevelForXp(xpCost)
val cost = AnvilCost()
cost.recipe = if (recipe.removeExactLinearXp) AnvilXpUtil.calculateMinimumLevelForXp(xpCost)
else AnvilXpUtil.calculateLevelForXp(xpCost)
val finalResult = DependencyManager.tryTreatAnvilResult(event, resultItem, AnvilUseType.CUSTOM_CRAFT, levelCost)
val finalResult = DependencyManager.tryTreatAnvilResult(event, resultItem, AnvilUseType.CUSTOM_CRAFT, cost)
if (finalResult == null) return false
event.result = finalResult.result
if (finalResult.result.isAir) return false
AnvilXpUtil.setAnvilInvXp(inventory, event.view, player, finalResult.levelCost, true)
AnvilXpUtil.setAnvilInvCost(inventory, event.view, player, cost, true)
return true
}
@ -217,7 +217,8 @@ class PrepareAnvilListener : Listener {
player: HumanEntity, first: ItemStack
) {
val resultItem = DependencyManager.cloneItem(event, first)
var anvilCost = handleRename(resultItem, inventory, player)
val cost = AnvilCost()
cost.rename = handleRename(resultItem, inventory, player)
// Test/stop if nothing changed.
if (first == resultItem) {
@ -226,15 +227,15 @@ class PrepareAnvilListener : Listener {
return
}
anvilCost += AnvilXpUtil.calculatePenalty(first, null, resultItem, AnvilUseType.RENAME_ONLY)
cost.penalty = AnvilXpUtil.calculatePenalty(first, null, resultItem, AnvilUseType.RENAME_ONLY)
val finalResult = DependencyManager.tryTreatAnvilResult(event, resultItem, AnvilUseType.RENAME_ONLY, anvilCost)
val finalResult = DependencyManager.tryTreatAnvilResult(event, resultItem, AnvilUseType.RENAME_ONLY, cost)
if (finalResult == null) return
event.result = finalResult.result
if (finalResult.result.isAir) return
AnvilXpUtil.setAnvilInvXp(inventory, event.view, player, finalResult.levelCost)
AnvilXpUtil.setAnvilInvCost(inventory, event.view, player, cost)
}
private fun handleRename(resultItem: ItemStack, inventory: AnvilInventory, player: HumanEntity): Int {
@ -291,18 +292,18 @@ class PrepareAnvilListener : Listener {
var hasChanged = !isIdentical(first.findEnchantments(), newEnchants)
val resultItem = DependencyManager.cloneItem(event, first)
var anvilCost = 0
val cost = AnvilCost()
if(hasChanged){
resultItem.setEnchantmentsUnsafe(newEnchants)
// Calculate enchantment cost
anvilCost+= AnvilXpUtil.getRightValues(second, resultItem)
cost.enchantment = AnvilXpUtil.getRightValues(second, resultItem)
}
// Calculate repair cost
if (!first.isEnchantedBook() && !second.isEnchantedBook()) {
// we only need to be concerned with repair when neither item is a book
val repaired = resultItem.repairFrom(first, second)
anvilCost += if (repaired) ConfigOptions.itemRepairCost else 0
cost.repair = if (repaired) ConfigOptions.itemRepairCost else 0
hasChanged = hasChanged || repaired
}
@ -313,18 +314,18 @@ class PrepareAnvilListener : Listener {
return
}
// As calculatePenalty edit result, we need to calculate penalty after checking equality
anvilCost += AnvilXpUtil.calculatePenalty(first, second, resultItem, AnvilUseType.MERGE)
cost.penalty = AnvilXpUtil.calculatePenalty(first, second, resultItem, AnvilUseType.MERGE)
// Calculate rename cost
anvilCost += handleRename(resultItem, inventory, player)
cost.rename = handleRename(resultItem, inventory, player)
// Finally, we set result
val finalResult = DependencyManager.tryTreatAnvilResult(event, resultItem, AnvilUseType.MERGE, anvilCost)
val finalResult = DependencyManager.tryTreatAnvilResult(event, resultItem, AnvilUseType.MERGE, cost)
if (finalResult == null) return
event.result = finalResult.result
if (finalResult.result.isAir) return
AnvilXpUtil.setAnvilInvXp(inventory, event.view, player, finalResult.levelCost)
AnvilXpUtil.setAnvilInvCost(inventory, event.view, player, cost)
}
private fun isIdentical(
@ -347,14 +348,15 @@ class PrepareAnvilListener : Listener {
val unitRepairAmount = first.getRepair(second) ?: return false
val resultItem = DependencyManager.cloneItem(event, first)
var anvilCost = handleRename(resultItem, inventory, player)
val cost = AnvilCost()
cost.rename = handleRename(resultItem, inventory, player)
val repairAmount = resultItem.unitRepair(second.amount, unitRepairAmount)
if (repairAmount > 0) {
anvilCost += repairAmount * ConfigOptions.unitRepairCost
cost.repair = repairAmount * ConfigOptions.unitRepairCost
}
// We do not care about right item penalty for unit repair
anvilCost += AnvilXpUtil.calculatePenalty(first, null, resultItem, AnvilUseType.UNIT_REPAIR)
cost.penalty = AnvilXpUtil.calculatePenalty(first, null, resultItem, AnvilUseType.UNIT_REPAIR)
// Test/stop if nothing changed.
if (first == resultItem) {
@ -363,13 +365,13 @@ class PrepareAnvilListener : Listener {
return true
}
val finalResult = DependencyManager.tryTreatAnvilResult(event, resultItem, AnvilUseType.UNIT_REPAIR, anvilCost)
val finalResult = DependencyManager.tryTreatAnvilResult(event, resultItem, AnvilUseType.UNIT_REPAIR, cost)
if (finalResult == null) return false
event.result = finalResult.result
if (finalResult.result.isAir) return false
AnvilXpUtil.setAnvilInvXp(inventory, event.view, player, finalResult.levelCost)
AnvilXpUtil.setAnvilInvCost(inventory, event.view, player, cost)
return true
}
@ -380,11 +382,11 @@ class PrepareAnvilListener : Listener {
val type = second.type
var result: ItemStack? = null
val xpCost = AtomicInteger()
val cost = AnvilCost()
if (Material.WRITABLE_BOOK == type) {
result = AnvilLoreEditUtil.tryLoreEditByBook(player, first, second, xpCost)
result = AnvilLoreEditUtil.tryLoreEditByBook(player, first, second, cost)
} else if (Material.PAPER == type) {
result = AnvilLoreEditUtil.tryLoreEditByPaper(player, first, second, xpCost)
result = AnvilLoreEditUtil.tryLoreEditByPaper(player, first, second, cost)
}
if (result.isAir || first == result) {
@ -394,7 +396,7 @@ class PrepareAnvilListener : Listener {
}
event.result = result
AnvilXpUtil.setAnvilInvXp(inventory, event.view, player, xpCost.get())
AnvilXpUtil.setAnvilInvCost(inventory, event.view, player, cost)
return true
}
}

View file

@ -8,10 +8,10 @@ import org.bukkit.permissions.Permissible
import xyz.alexcrea.cuanvil.dependency.DependencyManager
import xyz.alexcrea.cuanvil.dependency.util.PlatformUtil.componentLore
import xyz.alexcrea.cuanvil.dependency.util.PlatformUtil.setComponentLore
import xyz.alexcrea.cuanvil.util.AnvilXpUtil.AnvilCost
import xyz.alexcrea.cuanvil.util.config.LoreEditConfigUtil
import xyz.alexcrea.cuanvil.util.config.LoreEditType
import java.util.*
import java.util.concurrent.atomic.AtomicInteger
import java.util.concurrent.atomic.AtomicReference
object AnvilLoreEditUtil {
@ -31,7 +31,7 @@ object AnvilLoreEditUtil {
player: Permissible,
first: ItemStack,
book: BookMeta,
xpCost: AtomicInteger
cost: AnvilCost
): ItemStack? {
if (!hasLoreEditByBookPermission(player)) return null
@ -53,14 +53,14 @@ object AnvilLoreEditUtil {
if (result == first) return null
// Handle xp
xpCost.addAndGet(colorCost) // Cost of using color
xpCost.addAndGet(outLines.size * LoreEditType.APPEND_BOOK.perLineCost) // per line cost
xpCost.addAndGet(baseEditLoreXpCost(first, result, LoreEditType.APPEND_BOOK)) // Fixed cost and work penalty
cost.lore = colorCost // Cost of using color
cost.lore += outLines.size * LoreEditType.APPEND_BOOK.perLineCost // per line cost
baseEditLoreXpCost(cost, first, result, LoreEditType.APPEND_BOOK) // Fixed cost and work penalty
return result
}
fun handleLoreRemoveByBook(player: Permissible, first: ItemStack, xpCost: AtomicInteger): ItemStack? {
fun handleLoreRemoveByBook(player: Permissible, first: ItemStack, cost: AnvilCost): ItemStack? {
if (!hasLoreEditByBookPermission(player)) return null
// remove lore
@ -78,9 +78,9 @@ object AnvilLoreEditUtil {
if (result == first) return null
// Handle xp
xpCost.addAndGet(uncolorCost)
xpCost.addAndGet(currentLore.size * LoreEditType.REMOVE_BOOK.perLineCost)
xpCost.addAndGet(baseEditLoreXpCost(first, result, LoreEditType.REMOVE_BOOK))
cost.lore = uncolorCost
cost.lore+= currentLore.size * LoreEditType.REMOVE_BOOK.perLineCost
baseEditLoreXpCost(cost, first, result, LoreEditType.REMOVE_BOOK)
return result
}
@ -116,12 +116,12 @@ object AnvilLoreEditUtil {
return null
}
fun tryLoreEditByBook(player: HumanEntity, first: ItemStack, second: ItemStack, xpCost: AtomicInteger): ItemStack? {
fun tryLoreEditByBook(player: HumanEntity, first: ItemStack, second: ItemStack, cost: AnvilCost): ItemStack? {
val isAppend = bookLoreEditIsAppend(first, second) ?: return null
val meta = second.itemMeta as BookMeta
return if (isAppend) handleLoreAppendByBook(player, first, meta, xpCost)
else handleLoreRemoveByBook(player, first, xpCost)
return if (isAppend) handleLoreAppendByBook(player, first, meta, cost)
else handleLoreRemoveByBook(player, first, cost)
}
// Return true if appended, false if removed, null if neither
@ -147,7 +147,7 @@ object AnvilLoreEditUtil {
player: Permissible,
first: ItemStack,
second: ItemStack,
xpCost: AtomicInteger
cost: AnvilCost
): ItemStack? {
if (!hasLoreEditByPaperPermission(player)) return null
@ -175,13 +175,13 @@ object AnvilLoreEditUtil {
if (result == first) return null
// Handle xp
xpCost.addAndGet(colorCost)
xpCost.addAndGet(baseEditLoreXpCost(first, result, LoreEditType.APPEND_PAPER))
cost.lore = colorCost
baseEditLoreXpCost(cost, first, result, LoreEditType.APPEND_PAPER)
return result
}
fun handleLoreRemoveByPaper(player: Permissible, first: ItemStack, xpCost: AtomicInteger): ItemStack? {
fun handleLoreRemoveByPaper(player: Permissible, first: ItemStack, cost: AnvilCost): ItemStack? {
if (!hasLoreEditByPaperPermission(player)) return null
// remove lore line
@ -213,8 +213,8 @@ object AnvilLoreEditUtil {
val uncolorCost = uncolorLine(player, line, LoreEditType.REMOVE_PAPER)
// Handle other xp
xpCost.addAndGet(uncolorCost)
xpCost.addAndGet(baseEditLoreXpCost(first, result, LoreEditType.REMOVE_PAPER))
cost.lore = uncolorCost
baseEditLoreXpCost(cost, first, result, LoreEditType.REMOVE_PAPER)
return result
}
@ -223,23 +223,23 @@ object AnvilLoreEditUtil {
player: HumanEntity,
first: ItemStack,
second: ItemStack,
xpCost: AtomicInteger
cost: AnvilCost
): ItemStack? {
val isAppend = paperLoreEditIsAppend(first, second) ?: return null
return if (isAppend) handleLoreAppendByPaper(player, first, second, xpCost)
else handleLoreRemoveByPaper(player, first, xpCost)
return if (isAppend) handleLoreAppendByPaper(player, first, second, cost)
else handleLoreRemoveByPaper(player, first, cost)
}
private fun baseEditLoreXpCost(
cost: AnvilCost,
first: ItemStack,
result: ItemStack,
editType: LoreEditType
): Int {
var xpCost = editType.fixedCost
) {
cost.lore+= editType.fixedCost
xpCost += AnvilXpUtil.calculatePenalty(first, null, result, editType.useType)
return xpCost
cost.penalty = AnvilXpUtil.calculatePenalty(first, null, result, editType.useType)
}
fun colorPermission(player: Permissible, editType: LoreEditType): AnvilColorUtil.ColorPermissions {

View file

@ -23,16 +23,55 @@ object AnvilXpUtil {
const val EXCLUSIVE_PENALTY_PREFIX = "repair_cost"
class AnvilCost {
private val isAlone: Boolean
var generic = 0
var enchantment = 0
var repair = 0
var rename = 0
var lore = 0
var penalty = 0
var recipe = 0
fun sum(): Int {
return generic + enchantment + repair + rename + lore + penalty + recipe
}
constructor(generic: Int) {
this.generic = generic
isAlone = true
}
constructor() {
isAlone = false
}
}
/**
* Display the required cost (either as xp or as )
*/
fun setAnvilInvCost(
inventory: AnvilInventory,
view: InventoryView,
player: HumanEntity,
cost: AnvilCost,
ignoreRules: Boolean = false
) {
// TODO check require money or xp cost & display appropriately
setAnvilInvXp(inventory, view, player, cost.sum(), ignoreRules)
}
/**
* Display xp needed for the work on the anvil inventory
*/
fun setAnvilInvXp(
private fun setAnvilInvXp(
inventory: AnvilInventory,
view: InventoryView,
player: HumanEntity,
anvilCost: Int,
ignoreRules: Boolean = false
) {
// Test repair cost limit
val finalAnvilCost = if (
!ignoreRules &&
@ -78,7 +117,6 @@ object AnvilXpUtil {
}
player.updateInventory()
}
}