mirror of
https://gitlab.com/phoenix-dvpmt/mmoitems.git
synced 2025-01-24 09:51:21 +01:00
Fixed an issue with item lore
This commit is contained in:
parent
1178709a78
commit
dd0fb95cd2
@ -37,227 +37,251 @@ import java.util.UUID;
|
|||||||
import java.util.logging.Level;
|
import java.util.logging.Level;
|
||||||
|
|
||||||
public class ItemStackBuilder {
|
public class ItemStackBuilder {
|
||||||
@NotNull private final MMOItem mmoitem;
|
@NotNull
|
||||||
|
private final MMOItem mmoitem;
|
||||||
|
|
||||||
private final ItemStack item;
|
private final ItemStack item;
|
||||||
private final ItemMeta meta;
|
private final ItemMeta meta;
|
||||||
private final LoreBuilder lore;
|
private final LoreBuilder lore;
|
||||||
private final List<ItemTag> tags = new ArrayList<>();
|
private final List<ItemTag> tags = new ArrayList<>();
|
||||||
|
|
||||||
private static final AttributeModifier fakeModifier = new AttributeModifier(
|
private static final AttributeModifier fakeModifier = new AttributeModifier(
|
||||||
UUID.fromString("87851e28-af12-43f6-898e-c62bde6bd0ec"), "mmoitemsDecoy", 0, Operation.ADD_NUMBER);
|
UUID.fromString("87851e28-af12-43f6-898e-c62bde6bd0ec"), "mmoitemsDecoy", 0, Operation.ADD_NUMBER);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Used to build an MMOItem into an ItemStack.
|
* Used to build an MMOItem into an ItemStack.
|
||||||
*
|
*
|
||||||
* @param mmoitem The mmoitem you want to build
|
* @param mmoitem The mmoitem you want to build
|
||||||
*/
|
*/
|
||||||
public ItemStackBuilder(@NotNull MMOItem mmoitem) {
|
public ItemStackBuilder(@NotNull MMOItem mmoitem) {
|
||||||
|
|
||||||
// Reference to source MMOItem
|
// Reference to source MMOItem
|
||||||
this.mmoitem = mmoitem;
|
this.mmoitem = mmoitem;
|
||||||
|
|
||||||
// Generates a new ItemStack of the specified material (Specified in the Material stat, or a DIAMOND_SWORD if missing).
|
// Generates a new ItemStack of the specified material (Specified in the Material stat, or a DIAMOND_SWORD if missing).
|
||||||
item = new ItemStack( mmoitem.hasData(ItemStats.MATERIAL) ?
|
item = new ItemStack(mmoitem.hasData(ItemStats.MATERIAL) ?
|
||||||
((MaterialData) mmoitem.getData(ItemStats.MATERIAL)).getMaterial()
|
((MaterialData) mmoitem.getData(ItemStats.MATERIAL)).getMaterial()
|
||||||
: Material.DIAMOND_SWORD);
|
: Material.DIAMOND_SWORD);
|
||||||
|
|
||||||
// Gets a lore builder, which will be used to apply the chosen lore format (Choose with the lore format stat, or the default one if unspecified)
|
// Gets a lore builder, which will be used to apply the chosen lore format (Choose with the lore format stat, or the default one if unspecified)
|
||||||
lore = new LoreBuilder(mmoitem.hasData(ItemStats.LORE_FORMAT)
|
lore = new LoreBuilder(mmoitem.hasData(ItemStats.LORE_FORMAT)
|
||||||
? MMOItems.plugin.getFormats().getFormat(mmoitem.getData(ItemStats.LORE_FORMAT).toString())
|
? MMOItems.plugin.getFormats().getFormat(mmoitem.getData(ItemStats.LORE_FORMAT).toString())
|
||||||
: MMOItems.plugin.getLanguage().getDefaultLoreFormat());
|
: MMOItems.plugin.getLanguage().getDefaultLoreFormat());
|
||||||
|
|
||||||
// Gets the meta, and hides attributes
|
// Gets the meta, and hides attributes
|
||||||
meta = item.getItemMeta();
|
meta = item.getItemMeta();
|
||||||
meta.addItemFlags(ItemFlag.HIDE_ATTRIBUTES);
|
meta.addItemFlags(ItemFlag.HIDE_ATTRIBUTES);
|
||||||
|
|
||||||
// Store the internal TYPE-ID Information (not stats, so it must be done manually here)
|
// Store the internal TYPE-ID Information (not stats, so it must be done manually here)
|
||||||
tags.add(new ItemTag("MMOITEMS_ITEM_TYPE", mmoitem.getType().getId()));
|
tags.add(new ItemTag("MMOITEMS_ITEM_TYPE", mmoitem.getType().getId()));
|
||||||
tags.add(new ItemTag("MMOITEMS_ITEM_ID", mmoitem.getId()));
|
tags.add(new ItemTag("MMOITEMS_ITEM_ID", mmoitem.getId()));
|
||||||
|
|
||||||
// And a last technical tag for updating items
|
// And a last technical tag for updating items
|
||||||
if (MMOItems.INTERNAL_REVISION_ID > 1) { tags.add(new ItemTag("MMOITEMS_INTERNAL_REVISION_ID", MMOItems.INTERNAL_REVISION_ID)); }
|
if (MMOItems.INTERNAL_REVISION_ID > 1) {
|
||||||
|
tags.add(new ItemTag("MMOITEMS_INTERNAL_REVISION_ID", MMOItems.INTERNAL_REVISION_ID));
|
||||||
|
}
|
||||||
/*if (MMOItems.plugin.getUpdater().hasData(mmoitem))
|
/*if (MMOItems.plugin.getUpdater().hasData(mmoitem))
|
||||||
tags.add(new ItemTag("MMOITEMS_ITEM_UUID",
|
tags.add(new ItemTag("MMOITEMS_ITEM_UUID",
|
||||||
MMOItems.plugin.getUpdater().getData(mmoitem.getType(), mmoitem.getId()).getUniqueId().toString()));*/
|
MMOItems.plugin.getUpdater().getData(mmoitem.getType(), mmoitem.getId()).getUniqueId().toString()));*/
|
||||||
}
|
}
|
||||||
|
|
||||||
public LoreBuilder getLore() { return lore; }
|
public LoreBuilder getLore() {
|
||||||
|
return lore;
|
||||||
|
}
|
||||||
|
|
||||||
@NotNull public MMOItem getMMOItem() { return mmoitem; }
|
@NotNull
|
||||||
|
public MMOItem getMMOItem() {
|
||||||
|
return mmoitem;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @return Does NOT return the built item stack. It returns only returns the
|
* @return Does NOT return the built item stack. It returns only returns the
|
||||||
* default item stack with material applied. Built item stack is given
|
* default item stack with material applied. Built item stack is given
|
||||||
* by build(). This method should only be used to check if the item is
|
* by build(). This method should only be used to check if the item is
|
||||||
* of a specific material (like the Shield Pattern stat which checks if
|
* of a specific material (like the Shield Pattern stat which checks if
|
||||||
* the item is a shield)
|
* the item is a shield)
|
||||||
*/
|
*/
|
||||||
public ItemStack getItemStack() { return item; }
|
public ItemStack getItemStack() {
|
||||||
|
return item;
|
||||||
|
}
|
||||||
|
|
||||||
public ItemMeta getMeta() { return meta; }
|
public ItemMeta getMeta() {
|
||||||
|
return meta;
|
||||||
|
}
|
||||||
|
|
||||||
public void addItemTag(List<ItemTag> newTags) { tags.addAll(newTags); }
|
public void addItemTag(List<ItemTag> newTags) {
|
||||||
|
tags.addAll(newTags);
|
||||||
|
}
|
||||||
|
|
||||||
public void addItemTag(ItemTag... itemTags) { tags.addAll(Arrays.asList(itemTags)); }
|
public void addItemTag(ItemTag... itemTags) {
|
||||||
|
tags.addAll(Arrays.asList(itemTags));
|
||||||
|
}
|
||||||
|
|
||||||
public static final String history_keyword = "HSTRY_";
|
public static final String history_keyword = "HSTRY_";
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @return Returns built NBTItem with applied tags and lore
|
* @return Returns built NBTItem with applied tags and lore
|
||||||
*/
|
*/
|
||||||
public NBTItem buildNBT() { return buildNBT(false); }
|
public NBTItem buildNBT() {
|
||||||
|
return buildNBT(false);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @return Returns built NBTItem with applied tags and lore
|
* @param forDisplay Should this item's lore display potential stats
|
||||||
*
|
* (like RNG ranges before rolling) rather than the
|
||||||
* @param forDisplay Should this item's lore display potential stats
|
* stats it will have?
|
||||||
* (like RNG ranges before rolling) rather than the
|
* @return Returns built NBTItem with applied tags and lore
|
||||||
* stats it will have?
|
*/
|
||||||
*/
|
public NBTItem buildNBT(boolean forDisplay) {
|
||||||
public NBTItem buildNBT(boolean forDisplay) {
|
// Clone as to not conflict in any way
|
||||||
// Clone as to not conflict in any way
|
MMOItem builtMMOItem = mmoitem.clone();
|
||||||
MMOItem builtMMOItem = mmoitem.clone();
|
//GEM//MMOItems.log("\u00a7e+ \u00a77Building \u00a7c" + mmoitem.getType().getName() + " " + mmoitem.getId() + "\u00a77 (Size \u00a7e" + mmoitem.getStatHistories().size() + "\u00a77 Historic)");
|
||||||
//GEM//MMOItems.log("\u00a7e+ \u00a77Building \u00a7c" + mmoitem.getType().getName() + " " + mmoitem.getId() + "\u00a77 (Size \u00a7e" + mmoitem.getStatHistories().size() + "\u00a77 Historic)");
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* As an assumption for several enchantment recognition operations,
|
* As an assumption for several enchantment recognition operations,
|
||||||
* Enchantment data must never be clear and lack history. This is
|
* Enchantment data must never be clear and lack history. This is
|
||||||
* the basis for when an item is 'old'
|
* the basis for when an item is 'old'
|
||||||
*/
|
*/
|
||||||
if (!builtMMOItem.hasData(ItemStats.ENCHANTS)) { builtMMOItem.setData(ItemStats.ENCHANTS, ItemStats.ENCHANTS.getClearStatData()); }
|
if (!builtMMOItem.hasData(ItemStats.ENCHANTS)) {
|
||||||
//GEM// else {MMOItems.log("\u00a73 -?- \u00a77Apparently found enchantment data \u00a7b" + (mmoitem.getData(ItemStats.ENCHANTS) == null ? "null" : ((EnchantListData) mmoitem.getData(ItemStats.ENCHANTS)).getEnchants().size())); }
|
builtMMOItem.setData(ItemStats.ENCHANTS, ItemStats.ENCHANTS.getClearStatData());
|
||||||
|
}
|
||||||
|
//GEM// else {MMOItems.log("\u00a73 -?- \u00a77Apparently found enchantment data \u00a7b" + (mmoitem.getData(ItemStats.ENCHANTS) == null ? "null" : ((EnchantListData) mmoitem.getData(ItemStats.ENCHANTS)).getEnchants().size())); }
|
||||||
|
|
||||||
// For every stat within this item
|
// For every stat within this item
|
||||||
for (ItemStat stat : builtMMOItem.getStats())
|
for (ItemStat stat : builtMMOItem.getStats())
|
||||||
|
|
||||||
// Attempt to add
|
// Attempt to add
|
||||||
try {
|
try {
|
||||||
|
|
||||||
//GEM//MMOItems.log("\u00a7e -+- \u00a77Applying \u00a76" + stat.getNBTPath());
|
//GEM//MMOItems.log("\u00a7e -+- \u00a77Applying \u00a76" + stat.getNBTPath());
|
||||||
|
|
||||||
// Does the item have any stat history regarding thay?
|
// Does the item have any stat history regarding thay?
|
||||||
StatHistory s = builtMMOItem.getStatHistory(stat); int l = mmoitem.getUpgradeLevel();
|
StatHistory s = builtMMOItem.getStatHistory(stat);
|
||||||
|
int l = mmoitem.getUpgradeLevel();
|
||||||
|
|
||||||
// Found it?
|
// Found it?
|
||||||
if (s != null) {
|
if (s != null) {
|
||||||
//GEM//MMOItems.log("\u00a7a -+- \u00a77History exists...");
|
//GEM//MMOItems.log("\u00a7a -+- \u00a77History exists...");
|
||||||
//GEM//s.log();
|
//GEM//s.log();
|
||||||
|
|
||||||
// Recalculate
|
// Recalculate
|
||||||
//HSY//MMOItems.log(" \u00a73-\u00a7a- \u00a77ItemStack Building Recalculation \u00a73-\u00a7a-\u00a73-\u00a7a-\u00a73-\u00a7a-\u00a73-\u00a7a-");
|
//HSY//MMOItems.log(" \u00a73-\u00a7a- \u00a77ItemStack Building Recalculation \u00a73-\u00a7a-\u00a73-\u00a7a-\u00a73-\u00a7a-\u00a73-\u00a7a-");
|
||||||
builtMMOItem.setData(stat, s.recalculate(l));
|
builtMMOItem.setData(stat, s.recalculate(l));
|
||||||
|
|
||||||
// Add to NBT, if the gemstones were not purged
|
// Add to NBT, if the gemstones were not purged
|
||||||
if ((!s.isClear() || stat instanceof Enchants || stat instanceof DisplayName)) {
|
if ((!s.isClear() || stat instanceof Enchants || stat instanceof DisplayName)) {
|
||||||
|
|
||||||
//GEM//MMOItems.log("\u00a7a -+- \u00a77Recording History");
|
//GEM//MMOItems.log("\u00a7a -+- \u00a77Recording History");
|
||||||
addItemTag(new ItemTag(history_keyword + stat.getId(), s.toNBTString())); }
|
addItemTag(new ItemTag(history_keyword + stat.getId(), s.toNBTString()));
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (forDisplay && stat instanceof Previewable) {
|
if (forDisplay && stat instanceof Previewable) {
|
||||||
|
|
||||||
// Get Template
|
// Get Template
|
||||||
MMOItemTemplate template = MMOItems.plugin.getTemplates().getTemplate(builtMMOItem.getType(), builtMMOItem.getId());
|
MMOItemTemplate template = MMOItems.plugin.getTemplates().getTemplate(builtMMOItem.getType(), builtMMOItem.getId());
|
||||||
if (template == null) { throw new IllegalArgumentException("MMOItem $r" + builtMMOItem.getType().getId() + " " + builtMMOItem.getId() + "$b doesn't exist."); }
|
if (template == null) {
|
||||||
|
throw new IllegalArgumentException("MMOItem $r" + builtMMOItem.getType().getId() + " " + builtMMOItem.getId() + "$b doesn't exist.");
|
||||||
|
}
|
||||||
|
|
||||||
// Make necessary lore changes
|
// Make necessary lore changes
|
||||||
((Previewable) stat).whenPreviewed(this, builtMMOItem.getData(stat), template.getBaseItemData().get(stat));
|
((Previewable) stat).whenPreviewed(this, builtMMOItem.getData(stat), template.getBaseItemData().get(stat));
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
|
|
||||||
// Make necessary lore changes
|
// Make necessary lore changes
|
||||||
stat.whenApplied(this, builtMMOItem.getData(stat));
|
stat.whenApplied(this, builtMMOItem.getData(stat));
|
||||||
}
|
}
|
||||||
|
|
||||||
// Something went wrong...
|
// Something went wrong...
|
||||||
} catch (IllegalArgumentException|NullPointerException exception) {
|
} catch (IllegalArgumentException | NullPointerException exception) {
|
||||||
|
|
||||||
// That
|
// That
|
||||||
MMOItems.plugin.getLogger().log(Level.WARNING, FriendlyFeedbackProvider.quickForConsole(FFPMMOItems.get(),
|
MMOItems.plugin.getLogger().log(Level.WARNING, FriendlyFeedbackProvider.quickForConsole(FFPMMOItems.get(),
|
||||||
"An error occurred while trying to generate item '$f{0}$b' with stat '$f{1}$b': {2}",
|
"An error occurred while trying to generate item '$f{0}$b' with stat '$f{1}$b': {2}",
|
||||||
builtMMOItem.getId(),
|
builtMMOItem.getId(),
|
||||||
stat.getId(),
|
stat.getId(),
|
||||||
exception.getMessage()));
|
exception.getMessage()));
|
||||||
}
|
}
|
||||||
|
|
||||||
// Display gem stone lore hint thing
|
// Display gem stone lore hint thing
|
||||||
if (builtMMOItem.getType() == Type.GEM_STONE)
|
if (builtMMOItem.getType() == Type.GEM_STONE)
|
||||||
lore.insert("gem-stone-lore", ItemStat.translate("gem-stone-lore"));
|
lore.insert("gem-stone-lore", ItemStat.translate("gem-stone-lore"));
|
||||||
|
|
||||||
// Display item type
|
// Display item type
|
||||||
lore.insert("item-type",
|
lore.insert("item-type",
|
||||||
ItemStat.translate("item-type").replace("#",
|
ItemStat.translate("item-type").replace("#",
|
||||||
builtMMOItem.getStats().contains(ItemStats.DISPLAYED_TYPE)
|
builtMMOItem.getStats().contains(ItemStats.DISPLAYED_TYPE)
|
||||||
? builtMMOItem.getData(ItemStats.DISPLAYED_TYPE).toString()
|
? builtMMOItem.getData(ItemStats.DISPLAYED_TYPE).toString()
|
||||||
: builtMMOItem.getType().getName()));
|
: builtMMOItem.getType().getName()));
|
||||||
|
|
||||||
// Calculate extra item lore with placeholders
|
// Calculate extra item lore with placeholders
|
||||||
if (builtMMOItem.hasData(ItemStats.LORE)) {
|
if (builtMMOItem.hasData(ItemStats.LORE)) {
|
||||||
List<String> parsed = new ArrayList<>();
|
List<String> parsed = new ArrayList<>();
|
||||||
((StringListData) builtMMOItem.getData(ItemStats.LORE)).getList()
|
((StringListData) builtMMOItem.getData(ItemStats.LORE)).getList()
|
||||||
.forEach(str -> parsed.add(lore.applySpecialPlaceholders(str)));
|
.forEach(str -> parsed.add(lore.applySpecialPlaceholders(str)));
|
||||||
lore.insert("lore", parsed);
|
lore.insert("lore", parsed);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Calculate item lore
|
// Calculate item lore
|
||||||
List<String> builtLore = lore.build();
|
List<String> builtLore = lore.build();
|
||||||
|
|
||||||
// TODO generalize this to all enchants plugins, not only MythicEnchants
|
// TODO generalize this to all enchants plugins, not only MythicEnchants
|
||||||
if (MMOItems.plugin.getMythicEnchantsSupport() != null && mmoitem.hasData(ItemStats.ENCHANTS)) {
|
if (MMOItems.plugin.getMythicEnchantsSupport() != null && mmoitem.hasData(ItemStats.ENCHANTS)) {
|
||||||
ItemStack metaItem = item.clone();
|
ItemStack metaItem = item.clone();
|
||||||
ItemMeta meta = metaItem.getItemMeta();
|
ItemMeta meta = metaItem.getItemMeta();
|
||||||
meta.setLore(builtLore);
|
meta.setLore(builtLore);
|
||||||
metaItem.setItemMeta(meta);
|
metaItem.setItemMeta(meta);
|
||||||
|
|
||||||
EnchantListData data = (EnchantListData) mmoitem.getData(ItemStats.ENCHANTS);
|
EnchantListData data = (EnchantListData) mmoitem.getData(ItemStats.ENCHANTS);
|
||||||
for (Enchantment enchant : data.getEnchants()) {
|
for (Enchantment enchant : data.getEnchants()) {
|
||||||
int lvl = data.getLevel(enchant);
|
int lvl = data.getLevel(enchant);
|
||||||
if (lvl != 0 && enchant instanceof MythicEnchant)
|
if (lvl != 0 && enchant instanceof MythicEnchant)
|
||||||
MMOItems.plugin.getMythicEnchantsSupport().handleEnchant(metaItem, enchant, lvl);
|
MMOItems.plugin.getMythicEnchantsSupport().handleEnchant(metaItem, enchant, lvl);
|
||||||
}
|
}
|
||||||
builtLore = metaItem.getItemMeta().getLore();
|
builtLore = metaItem.getItemMeta().getLore();
|
||||||
}
|
}
|
||||||
|
|
||||||
// Apply item lore
|
// Apply item lore
|
||||||
meta.setLore(builtLore);
|
meta.setLore(builtLore);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Save dynamic lore for later calculations. Not used anymore, but
|
* Save dynamic lore for later calculations. Not used anymore, but
|
||||||
* kept in case we need to roll back the lore update change.
|
* kept in case we need to roll back the lore update change.
|
||||||
*/
|
*/
|
||||||
JsonArray array = new JsonArray();
|
JsonArray array = new JsonArray();
|
||||||
builtLore.forEach(str -> array.add(str));
|
builtLore.forEach(str -> array.add(str));
|
||||||
if (array.size() != 0)
|
if (array.size() != 0)
|
||||||
tags.add(new ItemTag("MMOITEMS_DYNAMIC_LORE", array.toString()));
|
tags.add(new ItemTag("MMOITEMS_DYNAMIC_LORE", array.toString()));
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* This tag is added to entirely override default vanilla item attribute
|
* This tag is added to entirely override default vanilla item attribute
|
||||||
* modifiers, this way armor gives no ARMOR or ARMOR TOUGHNESS to the holder.
|
* modifiers, this way armor gives no ARMOR or ARMOR TOUGHNESS to the holder.
|
||||||
* Since 4.7 attributes are handled via custom calculations
|
* Since 4.7 attributes are handled via custom calculations
|
||||||
*/
|
*/
|
||||||
meta.addAttributeModifier(Attribute.GENERIC_ATTACK_SPEED, fakeModifier);
|
meta.addAttributeModifier(Attribute.GENERIC_ATTACK_SPEED, fakeModifier);
|
||||||
|
|
||||||
item.setItemMeta(meta);
|
item.setItemMeta(meta);
|
||||||
NBTItem nbtItem = NBTItem.get(item);
|
NBTItem nbtItem = NBTItem.get(item);
|
||||||
|
|
||||||
// Apply item display name using Components for colors
|
// Apply item display name using Components for colors
|
||||||
if (mmoitem.hasData(ItemStats.NAME) && meta.hasDisplayName())
|
if (mmoitem.hasData(ItemStats.NAME) && meta.hasDisplayName())
|
||||||
nbtItem.setDisplayNameComponent(LegacyComponent.parse(meta.getDisplayName()));
|
nbtItem.setDisplayNameComponent(LegacyComponent.parse(meta.getDisplayName()));
|
||||||
|
|
||||||
return nbtItem.addTag(tags);
|
return nbtItem.addTag(tags);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @return Builds the item
|
* @return Builds the item
|
||||||
*/
|
*/
|
||||||
public ItemStack build() {
|
public ItemStack build() {
|
||||||
return buildNBT().toItem();
|
return buildNBT().toItem();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @return Builds the item
|
* @return Builds the item
|
||||||
*/
|
*/
|
||||||
public ItemStack build(boolean forDisplay) {
|
public ItemStack build(boolean forDisplay) {
|
||||||
return buildNBT(forDisplay).toItem(); }
|
return buildNBT(forDisplay).toItem();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,10 +1,7 @@
|
|||||||
package net.Indyuce.mmoitems.api.item.build;
|
package net.Indyuce.mmoitems.api.item.build;
|
||||||
|
|
||||||
import com.google.common.collect.Lists;
|
import com.google.common.collect.Lists;
|
||||||
import com.google.gson.JsonArray;
|
|
||||||
import com.google.gson.JsonElement;
|
|
||||||
import io.lumine.mythic.lib.MythicLib;
|
import io.lumine.mythic.lib.MythicLib;
|
||||||
import io.lumine.mythic.lib.api.item.NBTItem;
|
|
||||||
import org.jetbrains.annotations.NotNull;
|
import org.jetbrains.annotations.NotNull;
|
||||||
|
|
||||||
import java.util.*;
|
import java.util.*;
|
||||||
@ -24,151 +21,154 @@ import java.util.*;
|
|||||||
* @author indyuce
|
* @author indyuce
|
||||||
*/
|
*/
|
||||||
public class LoreBuilder {
|
public class LoreBuilder {
|
||||||
private final List<String> lore = new ArrayList<>();
|
private final List<String> lore = new ArrayList<>();
|
||||||
private final List<String> end = new ArrayList<>();
|
private final List<String> end = new ArrayList<>();
|
||||||
private final Map<String, String> placeholders = new HashMap<>();
|
private final Map<String, String> placeholders = new HashMap<>();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Default constructor used when building items
|
* Default constructor used when building items
|
||||||
*
|
*
|
||||||
* @param format
|
* @param format
|
||||||
*/
|
*/
|
||||||
public LoreBuilder(Collection<String> format) {
|
public LoreBuilder(Collection<String> format) {
|
||||||
lore.addAll(format);
|
lore.addAll(format);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Inserts a list of strings in the item lore. The lines are added only if a
|
* Inserts a list of strings in the item lore. The lines are added only if a
|
||||||
* line #item-stat-id# can be found in the lore format.
|
* line #item-stat-id# can be found in the lore format.
|
||||||
*
|
*
|
||||||
* @param path The path of the stat, used to locate where to insert the stat
|
* @param path The path of the stat, used to locate where to insert the stat
|
||||||
* in the lore
|
* in the lore
|
||||||
* @param add The lines you want to add
|
* @param add The lines you want to add
|
||||||
*/
|
*/
|
||||||
public void insert(String path, String... add) {
|
public void insert(String path, String... add) {
|
||||||
int index = lore.indexOf("#" + path + "#");
|
int index = lore.indexOf("#" + path + "#");
|
||||||
if (index < 0)
|
if (index < 0)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
for (int j = 0; j < add.length; j++)
|
for (int j = 0; j < add.length; j++)
|
||||||
lore.add(index + 1, add[add.length - j - 1]);
|
lore.add(index + 1, add[add.length - j - 1]);
|
||||||
lore.remove(index);
|
lore.remove(index);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Inserts a list of strings in the item lore. The lines are added only if a
|
* Inserts a list of strings in the item lore. The lines are added only if a
|
||||||
* line #item-stat-id# can be found in the lore format.
|
* line #item-stat-id# can be found in the lore format.
|
||||||
*
|
*
|
||||||
* @param path The path of the stat, used to locate where to insert the stat
|
* @param path The path of the stat, used to locate where to insert the stat
|
||||||
* in the lore
|
* in the lore
|
||||||
* @param list The lines you want to add
|
* @param list The lines you want to add
|
||||||
*/
|
*/
|
||||||
public void insert(String path, List<String> list) {
|
public void insert(String path, List<String> list) {
|
||||||
int index = lore.indexOf("#" + path + "#");
|
int index = lore.indexOf("#" + path + "#");
|
||||||
if (index < 0)
|
if (index < 0)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
Lists.reverse(list).forEach(string -> lore.add(index + 1, string));
|
Lists.reverse(list).forEach(string -> lore.add(index + 1, string));
|
||||||
lore.remove(index);
|
lore.remove(index);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Registers a placeholder. All placeholders registered will be parsed when
|
* Registers a placeholder. All placeholders registered will be parsed when
|
||||||
* using applyLorePlaceholders(String)
|
* using applyLorePlaceholders(String)
|
||||||
*
|
*
|
||||||
* @param path The placeholder path (CASE SENSITIVE)
|
* @param path The placeholder path (CASE SENSITIVE)
|
||||||
* @param value The placeholder value which is instantly saved as a string
|
* @param value The placeholder value which is instantly saved as a string
|
||||||
* when registered
|
* when registered
|
||||||
*/
|
*/
|
||||||
public void registerPlaceholder(String path, Object value) {
|
public void registerPlaceholder(String path, Object value) {
|
||||||
placeholders.put(path, value.toString());
|
placeholders.put(path, value.toString());
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Parses a string with registered special placeholders
|
* Parses a string with registered special placeholders
|
||||||
*
|
*
|
||||||
* @param str String with {..} unformatted placeholders
|
* @param str String with {..} unformatted placeholders
|
||||||
* @return Same string with replaced placeholders. Placeholders which
|
* @return Same string with replaced placeholders. Placeholders which
|
||||||
* couldn't be found are marked with PHE which means
|
* couldn't be found are marked with PHE which means
|
||||||
* PlaceHolderError
|
* PlaceHolderError
|
||||||
*/
|
*/
|
||||||
public String applySpecialPlaceholders(String str) {
|
public String applySpecialPlaceholders(String str) {
|
||||||
|
|
||||||
while (str.contains("{") && str.substring(str.indexOf("{")).contains("}")) {
|
while (str.contains("{") && str.substring(str.indexOf("{")).contains("}")) {
|
||||||
String holder = str.substring(str.indexOf("{") + 1, str.indexOf("}"));
|
String holder = str.substring(str.indexOf("{") + 1, str.indexOf("}"));
|
||||||
str = str.replace("{" + holder + "}", placeholders.getOrDefault(holder, "PHE"));
|
str = str.replace("{" + holder + "}", placeholders.getOrDefault(holder, "PHE"));
|
||||||
}
|
}
|
||||||
|
|
||||||
return str;
|
return str;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Adds a line of lore at the end of it
|
* Adds a line of lore at the end of it
|
||||||
*
|
*
|
||||||
* @param str String to insert at the end
|
* @param str String to insert at the end
|
||||||
*/
|
*/
|
||||||
public void end(@NotNull String str) {
|
public void end(@NotNull String str) {
|
||||||
end.add(str);
|
end.add(str);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @return A built item lore. This method must be called after all lines
|
* @return A built item lore. This method must be called after all lines
|
||||||
* have been inserted in the lore. It cleans all unused static placeholders
|
* have been inserted in the lore. It cleans all unused static placeholders
|
||||||
* as well as lore bars. The dynamic placeholders still remain however.
|
* as well as lore bars. The dynamic placeholders still remain however.
|
||||||
*/
|
*/
|
||||||
public List<String> build() {
|
public List<String> build() {
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Loops backwards to remove all unused bars in one iteration only,
|
* Loops backwards to remove all unused bars in one iteration only,
|
||||||
* otherwise the stats under a bar gets removed after the bar is checked
|
* otherwise the stats under a bar gets removed after the bar is checked
|
||||||
*/
|
*/
|
||||||
for (int j = 0; j < lore.size(); ) {
|
for (int j = 0; j < lore.size(); ) {
|
||||||
int n = lore.size() - j - 1;
|
int n = lore.size() - j - 1;
|
||||||
String line = lore.get(n);
|
String line = lore.get(n);
|
||||||
|
|
||||||
// Remove unused static lore placeholders
|
// Remove unused static lore placeholders
|
||||||
if (line.startsWith("#"))
|
if (line.startsWith("#"))
|
||||||
lore.remove(n);
|
lore.remove(n);
|
||||||
|
|
||||||
// Remove useless lore stripes
|
// Remove useless lore stripes
|
||||||
else if (line.startsWith("{bar}") && (n == lore.size() - 1 || isBar(lore.get(n + 1))))
|
else if (line.startsWith("{bar}") && (n == lore.size() - 1 || isBar(lore.get(n + 1))))
|
||||||
lore.remove(n);
|
lore.remove(n);
|
||||||
|
|
||||||
else
|
else
|
||||||
j++;
|
j++;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Clear bar codes and parse chat colors only ONCE the bars have been
|
* Clear bar codes and parse chat colors only ONCE the bars have been
|
||||||
* successfully calculated. Also breaks lines containing \n (like breaks)
|
* successfully calculated. Also breaks lines containing \n (like breaks)
|
||||||
*
|
*
|
||||||
* Edit so that there is no need to create an additional array list
|
* Edit so that there is no need to create an additional array list
|
||||||
*/
|
*/
|
||||||
for (int j = 0; j < lore.size(); ) {
|
for (int j = 0; j < lore.size(); ) {
|
||||||
|
|
||||||
// Apply color codes and replace bar prefixes
|
// Apply color codes and replace bar prefixes
|
||||||
String str = MythicLib.plugin.parseColors(lore.get(j).replace("{bar}", "").replace("{sbar}", ""));
|
String str = MythicLib.plugin.parseColors(lore.get(j).replace("{bar}", "").replace("{sbar}", ""));
|
||||||
|
|
||||||
// Need to break down the line into multiple
|
// Need to break down the line into multiple
|
||||||
if (str.contains("\\n")) {
|
if (str.contains("\\n")) {
|
||||||
lore.remove(j);
|
String[] split = str.split("\\\\n");
|
||||||
|
for (int k = split.length - 1; k >= 0; k -= 1)
|
||||||
|
lore.add(j, split[k]);
|
||||||
|
|
||||||
String[] split = str.split("\\\\n");
|
// Remove the old element
|
||||||
for (int k = split.length - 1; k >= 0; k -= 1)
|
lore.remove(j + split.length);
|
||||||
lore.add(j + 1, split[k]);
|
|
||||||
|
|
||||||
j += split.length;
|
// Increment by the right amount
|
||||||
|
j += split.length;
|
||||||
|
|
||||||
// Simple line
|
} else
|
||||||
} else
|
|
||||||
lore.set(j++, str);
|
|
||||||
}
|
|
||||||
|
|
||||||
lore.addAll(end);
|
// Simple line
|
||||||
return lore;
|
lore.set(j++, str);
|
||||||
}
|
}
|
||||||
|
|
||||||
private boolean isBar(String str) {
|
lore.addAll(end);
|
||||||
return str.startsWith("{bar}") || str.startsWith("{sbar}");
|
return lore;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private boolean isBar(String str) {
|
||||||
|
return str.startsWith("{bar}") || str.startsWith("{sbar}");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user