Skip to content

Instantly share code, notes, and snippets.

@mzcydev
Created February 20, 2025 13:55
Show Gist options
  • Select an option

  • Save mzcydev/ae22b0a31a802ecedb5a22d2f73d3445 to your computer and use it in GitHub Desktop.

Select an option

Save mzcydev/ae22b0a31a802ecedb5a22d2f73d3445 to your computer and use it in GitHub Desktop.
Simple ItemBuilder for 1.20.4. Requires paperweight.paperDevBundle.
package dev.mzcy.util.builder.item;
import com.destroystokyo.paper.profile.PlayerProfile;
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
import com.google.gson.JsonObject;
import net.kyori.adventure.text.Component;
import net.minecraft.nbt.CompoundTag;
import net.minecraft.nbt.ListTag;
import org.bukkit.*;
import org.bukkit.craftbukkit.v1_20_R3.inventory.CraftItemStack;
import org.bukkit.enchantments.Enchantment;
import org.bukkit.entity.Item;
import org.bukkit.inventory.ItemFactory;
import org.bukkit.inventory.ItemFlag;
import org.bukkit.inventory.ItemStack;
import org.bukkit.inventory.meta.*;
import org.bukkit.persistence.PersistentDataType;
import org.bukkit.profile.PlayerTextures;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import java.net.MalformedURLException;
import java.net.URI;
import java.nio.charset.StandardCharsets;
import java.util.*;
/**
* A builder class for creating and manipulating ItemStack objects in Minecraft.
*/
public class ItemBuilder extends ItemStack implements Cloneable {
private static final Gson gson = new GsonBuilder().disableHtmlEscaping().setPrettyPrinting().create();
private ItemBuilder() {
super();
}
private ItemBuilder(@NotNull Material type) {
super(type);
}
private ItemBuilder(@NotNull Material type, int amount) {
super(type, amount);
}
@Deprecated(since = "1.0")
private ItemBuilder(@NotNull Material type, int amount, short damage) {
super(type, amount, damage);
}
@Deprecated(since = "1.0")
private ItemBuilder(@NotNull Material type, int amount, short damage, @Nullable Byte data) {
super(type, amount, damage, data);
}
private ItemBuilder(@NotNull ItemStack stack) throws IllegalArgumentException {
super(stack);
}
/**
* Creates a new ItemBuilder instance.
*
* @return a new ItemBuilder instance.
*/
public static ItemBuilder builder() {
return new ItemBuilder();
}
/**
* Creates a new ItemBuilder instance with the specified material type.
*
* @param type the material type.
* @return a new ItemBuilder instance.
*/
public static ItemBuilder builder(@NotNull Material type) {
return new ItemBuilder(type);
}
/**
* Creates a new ItemBuilder instance with the specified material type and amount.
*
* @param type the material type.
* @param amount the amount.
* @return a new ItemBuilder instance.
*/
public static ItemBuilder builder(@NotNull Material type, int amount) {
return new ItemBuilder(type, amount);
}
@Deprecated(since = "1.0")
public static ItemBuilder builder(@NotNull Material type, int amount, short damage) {
return new ItemBuilder(type, amount, damage);
}
@Deprecated(since = "1.0")
public static ItemBuilder builder(@NotNull Material type, int amount, short damage, @Nullable Byte data) {
return new ItemBuilder(type, amount, damage, data);
}
/**
* Creates a new ItemBuilder instance from an existing ItemStack.
*
* @param stack the existing ItemStack.
* @return a new ItemBuilder instance.
* @throws IllegalArgumentException if the stack is null.
*/
public static ItemBuilder builder(@NotNull ItemStack stack) {
return new ItemBuilder(stack);
}
/**
* Creates a new ItemBuilder instance from an existing ItemBuilder.
*
* @param builder the existing ItemBuilder.
* @return a new ItemBuilder instance.
*/
public static ItemBuilder builder(@NotNull ItemBuilder builder) {
return new ItemBuilder(builder);
}
/**
* Sets the material type of the item.
*
* @param type the material type.
* @return the current ItemBuilder instance.
*/
@SuppressWarnings("deprecation")
public ItemBuilder type(@NotNull Material type) {
this.setType(type);
return this;
}
/**
* Sets the amount of the item.
*
* @param amount the amount.
* @return the current ItemBuilder instance.
*/
public ItemBuilder amount(int amount) {
this.setAmount(amount);
return this;
}
/**
* Sets the damage value of the item.
*
* @param damage the damage value.
* @return the current ItemBuilder instance.
*/
public ItemBuilder damage(short damage) {
Damageable damageable = (Damageable) this.getItemMeta();
damageable.setDamage(damage);
setItemMeta(damageable);
return this;
}
/**
* Sets the display name of the item.
*
* @param name the display name.
* @return the current ItemBuilder instance.
*/
@SuppressWarnings("deprecation")
public ItemBuilder displayName(@NotNull String name) {
this.getItemMeta().setDisplayName(name);
return this;
}
/**
* Sets the display name of the item using a Component.
*
* @param name the display name as a Component.
* @return the current ItemBuilder instance.
*/
public ItemBuilder displayName(@NotNull Component name) {
this.getItemMeta().displayName(name);
return this;
}
/**
* Sets the lore of the item.
*
* @param lore the lore as an array of strings.
* @return the current ItemBuilder instance.
*/
public ItemBuilder lore(@NotNull String... lore) {
ItemMeta meta = this.getItemMeta();
meta.lore(Arrays.stream(lore).map(Component::text).toList());
this.setItemMeta(meta);
return this;
}
/**
* Sets the lore of the item using Components.
*
* @param lore the lore as an array of Components.
* @return the current ItemBuilder instance.
*/
public ItemBuilder lore(@NotNull Component... lore) {
ItemMeta meta = this.getItemMeta();
meta.lore(Arrays.asList(lore));
this.setItemMeta(meta);
return this;
}
/**
* Makes the item unbreakable.
*
* @return the current ItemBuilder instance.
*/
public ItemBuilder unbreakable() {
ItemMeta meta = this.getItemMeta();
meta.setUnbreakable(true);
this.setItemMeta(meta);
return this;
}
/**
* Adds an enchantment to the item.
*
* @param enchantment the enchantment.
* @param level the level of the enchantment.
* @return the current ItemBuilder instance.
*/
public ItemBuilder enchantment(Enchantment enchantment, int level) {
this.addUnsafeEnchantment(enchantment, level);
return this;
}
/**
* Adds an enchantment to the item with an option to ignore level restrictions.
*
* @param enchantment the enchantment.
* @param level the level of the enchantment.
* @param ignoreLevelRestriction whether to ignore level restrictions.
* @return the current ItemBuilder instance.
*/
public ItemBuilder enchantment(@NotNull Enchantment enchantment, int level, boolean ignoreLevelRestriction) {
this.addUnsafeEnchantment(enchantment, level);
return this;
}
/**
* Sets the custom model data of the item.
*
* @param data the custom model data.
* @return the current ItemBuilder instance.
*/
public ItemBuilder customModelData(int data) {
ItemMeta meta = this.getItemMeta();
meta.setCustomModelData(data);
this.setItemMeta(meta);
return this;
}
/**
* Adds item flags to the item.
*
* @param flags the item flags.
* @return the current ItemBuilder instance.
*/
public ItemBuilder itemFlags(@NotNull ItemFlag... flags) {
ItemMeta meta = this.getItemMeta();
meta.addItemFlags(flags);
this.setItemMeta(meta);
return this;
}
/**
* Clears the lore of the item.
*
* @return the current ItemBuilder instance.
*/
public ItemBuilder clearLore() {
ItemMeta meta = this.getItemMeta();
meta.lore(null);
this.setItemMeta(meta);
return this;
}
/**
* Clears all enchantments from the item.
*
* @return the current ItemBuilder instance.
*/
public ItemBuilder clearEnchantments() {
this.getEnchantments().keySet().forEach(this::removeEnchantment);
return this;
}
/**
* Clears all item flags from the item.
*
* @return the current ItemBuilder instance.
*/
public ItemBuilder clearItemFlags() {
ItemMeta meta = this.getItemMeta();
meta.removeItemFlags(ItemFlag.values());
this.setItemMeta(meta);
return this;
}
/**
* Sets the color of leather armor.
*
* @param color the dye color.
* @return the current ItemBuilder instance.
* @throws IllegalArgumentException if the item is not leather armor.
*/
public ItemBuilder leatherColor(DyeColor color) {
if (this.getType() != Material.LEATHER_BOOTS && this.getType() != Material.LEATHER_CHESTPLATE && this.getType() != Material.LEATHER_HELMET && this.getType() != Material.LEATHER_LEGGINGS) {
throw new IllegalArgumentException("leatherColor(DyeColor) can only be used on leather armor");
}
LeatherArmorMeta meta = (LeatherArmorMeta) this.getItemMeta();
meta.setColor(color.getColor());
this.setItemMeta(meta);
return this;
}
/**
* Sets the color of leather armor.
*
* @param color the color.
* @return the current ItemBuilder instance.
* @throws IllegalArgumentException if the item is not leather armor.
*/
public ItemBuilder leatherColor(Color color) {
if (this.getType() != Material.LEATHER_BOOTS && this.getType() != Material.LEATHER_CHESTPLATE && this.getType() != Material.LEATHER_HELMET && this.getType() != Material.LEATHER_LEGGINGS) {
throw new IllegalArgumentException("leatherColor(Color) can only be used on leather armor");
}
LeatherArmorMeta meta = (LeatherArmorMeta) this.getItemMeta();
this.setItemMeta(meta);
return this;
}
/**
* Sets the owner of a player head item.
*
* @param skullOwner the UUID of the player.
* @return the current ItemBuilder instance.
* @throws IllegalArgumentException if the item is not a player head.
*/
public ItemBuilder skullOwner(UUID skullOwner) {
if (this.getType() != Material.PLAYER_HEAD) {
throw new IllegalArgumentException("skullOwner(UUID) can only be used on PLAYER_HEAD");
}
SkullMeta skullMeta = (SkullMeta) this.getItemMeta();
PlayerProfile profile = Bukkit.createProfile(skullOwner);
skullMeta.setPlayerProfile(profile);
this.setItemMeta(skullMeta);
return this;
}
/**
* Sets the owner of a player head item.
*
* @param skullOwner the name of the player.
* @return the current ItemBuilder instance.
* @throws IllegalArgumentException if the item is not a player head.
*/
public ItemBuilder skullOwner(String skullOwner) {
if (this.getType() != Material.PLAYER_HEAD) {
throw new IllegalArgumentException("skullOwner(String) can only be used on PLAYER_HEAD");
}
SkullMeta skullMeta = (SkullMeta) this.getItemMeta();
skullMeta.setOwningPlayer(Bukkit.getOfflinePlayer(skullOwner));
this.setItemMeta(skullMeta);
return this;
}
/**
* Sets the texture of a player head item using a base64 string.
*
* @param base64 the base64 string of the texture.
* @return the current ItemBuilder instance.
* @throws IllegalArgumentException if the item is not a player head.
*/
public ItemBuilder skullTexture(String base64) {
return skullTexture(base64, PlayerTextures.SkinModel.SLIM);
}
/**
* Sets the texture of a player head item using a base64 string and skin model.
*
* @param base64 the base64 string of the texture.
* @param skinModel the skin model.
* @return the current ItemBuilder instance.
* @throws IllegalArgumentException if the item is not a player head or if the base64 string is invalid.
*/
public ItemBuilder skullTexture(String base64, PlayerTextures.SkinModel skinModel) {
if (this.getType() != Material.PLAYER_HEAD) {
throw new IllegalArgumentException("skullTexture(String) can only be used on PLAYER_HEAD");
}
byte[] decodedBytes = Base64.getDecoder().decode(base64);
PlayerProfile profile = Bukkit.createProfile(Bukkit.getOfflinePlayer("mzcy_").getUniqueId(), "crownplugins");
PlayerTextures textures = profile.getTextures();
JsonObject skinJson = gson.fromJson(new String(decodedBytes, StandardCharsets.UTF_8), JsonObject.class).getAsJsonObject("textures").getAsJsonObject("SKIN");
try {
textures.setSkin(URI.create(skinJson.get("url").getAsString()).toURL(), skinModel);
} catch (MalformedURLException e) {
throw new IllegalArgumentException("Invalid base64 string");
}
profile.setTextures(textures);
SkullMeta skullMeta = (SkullMeta) this.getItemMeta();
skullMeta.setPlayerProfile(profile);
this.setItemMeta(skullMeta);
return this;
}
/**
* Sets the color of a firework star item.
*
* @param colors the colors.
* @return the current ItemBuilder instance.
* @throws IllegalArgumentException if the item is not a firework star.
*/
public ItemBuilder fireworkColor(Color... colors) {
if (this.getType() != Material.FIREWORK_STAR) {
throw new IllegalArgumentException("fireworkColor(Color...) can only be used on FIREWORK_STAR");
}
FireworkMeta fireworkMeta = (FireworkMeta) this.getItemMeta();
fireworkMeta.addEffects(FireworkEffect.builder().withColor(colors).build());
fireworkMeta.addItemFlags(ItemFlag.HIDE_ITEM_SPECIFICS);
this.setItemMeta(fireworkMeta);
return this;
}
/**
* Sets the effect type of a firework star item.
*
* @param type the effect type.
* @return the current ItemBuilder instance.
* @throws IllegalArgumentException if the item is not a firework star.
*/
public ItemBuilder fireworkEffect(FireworkEffect.Type type) {
if (this.getType() != Material.FIREWORK_STAR) {
throw new IllegalArgumentException("fireworkEffect(FireworkEffect.Type) can only be used on FIREWORK_STAR");
}
FireworkMeta fireworkMeta = (FireworkMeta) this.getItemMeta();
fireworkMeta.addEffects(FireworkEffect.builder().with(type).build());
fireworkMeta.addItemFlags(ItemFlag.HIDE_ITEM_SPECIFICS);
this.setItemMeta(fireworkMeta);
return this;
}
/**
* Sets the effect type and colors of a firework star item.
*
* @param type the effect type.
* @param colors the colors.
* @return the current ItemBuilder instance.
* @throws IllegalArgumentException if the item is not a firework star.
*/
public ItemBuilder fireworkEffect(FireworkEffect.Type type, Color... colors) {
if (this.getType() != Material.FIREWORK_STAR) {
throw new IllegalArgumentException("fireworkEffect(FireworkEffect.Type, Color...) can only be used on FIREWORK_STAR");
}
FireworkMeta fireworkMeta = (FireworkMeta) this.getItemMeta();
fireworkMeta.addEffects(FireworkEffect.builder().with(type).withColor(colors).build());
fireworkMeta.addItemFlags(ItemFlag.HIDE_ITEM_SPECIFICS);
this.setItemMeta(fireworkMeta);
return this;
}
/**
* Sets the effect type, colors, and fade colors of a firework star item.
*
* @param type the effect type.
* @param colors the colors.
* @param fadeColors the fade colors.
* @return the current ItemBuilder instance.
* @throws IllegalArgumentException if the item is not a firework star.
*/
public ItemBuilder fireworkEffect(FireworkEffect.Type type, Color[] colors, Color[] fadeColors) {
if (this.getType() != Material.FIREWORK_STAR) {
throw new IllegalArgumentException("fireworkEffect(FireworkEffect.Type, Color[], Color[]) can only be used on FIREWORK_STAR");
}
FireworkMeta fireworkMeta = (FireworkMeta) this.getItemMeta();
fireworkMeta.addEffects(FireworkEffect.builder().with(type).withColor(colors).withFade(fadeColors).build());
fireworkMeta.addItemFlags(ItemFlag.HIDE_ITEM_SPECIFICS);
this.setItemMeta(fireworkMeta);
return this;
}
/**
* Sets the power of a firework star item.
*
* @param power the power.
* @return the current ItemBuilder instance.
* @throws IllegalArgumentException if the item is not a firework star.
*/
public ItemBuilder fireworkPower(int power) {
if (this.getType() != Material.FIREWORK_STAR) {
throw new IllegalArgumentException("fireworkPower(int) can only be used on FIREWORK_STAR");
}
FireworkMeta fireworkMeta = (FireworkMeta) this.getItemMeta();
fireworkMeta.setPower(power);
this.setItemMeta(fireworkMeta);
return this;
}
/**
* Sets the title of a book item.
*
* @param title the title.
* @return the current ItemBuilder instance.
* @throws IllegalArgumentException if the item is not a written or writable book.
*/
public ItemBuilder bookTitle(@NotNull String title) {
if (this.getType() != Material.WRITTEN_BOOK && this.getType() != Material.WRITABLE_BOOK) {
throw new IllegalArgumentException("bookTitle(String) can only be used on WRITTEN_BOOK and WRITABLE_BOOK");
}
BookMeta bookMeta = (BookMeta) this.getItemMeta();
bookMeta.setTitle(title);
this.setItemMeta(bookMeta);
return this;
}
/**
* Sets the author of a book item.
*
* @param author the name of the author.
* @return the current ItemBuilder instance.
* @throws IllegalArgumentException if the item is not a written or writable book.
*/
public ItemBuilder bookAuthor(@NotNull String author) {
if (this.getType() != Material.WRITTEN_BOOK && this.getType() != Material.WRITABLE_BOOK) {
throw new IllegalArgumentException("bookAuthor(String) can only be used on WRITTEN_BOOK and WRITABLE_BOOK");
}
BookMeta bookMeta = (BookMeta) this.getItemMeta();
bookMeta.setAuthor(author);
this.setItemMeta(bookMeta);
return this;
}
/**
* Adds a page to a book item with the specified content.
*
* @param page the page number.
* @param content the content of the page.
* @return the current ItemBuilder instance.
* @throws IllegalArgumentException if the item is not a written or writable book.
*/
public ItemBuilder bookPage(int page, @NotNull String content) {
if (this.getType() != Material.WRITTEN_BOOK && this.getType() != Material.WRITABLE_BOOK) {
throw new IllegalArgumentException("bookPage(int, String) can only be used on WRITTEN_BOOK and WRITABLE_BOOK");
}
BookMeta bookMeta = (BookMeta) this.getItemMeta();
bookMeta.addPages(Component.text(content));
this.setItemMeta(bookMeta);
return this;
}
/**
* Adds a page to a book item with the specified content.
*
* @param page the page number.
* @param content the content of the page as a Component.
* @return the current ItemBuilder instance.
* @throws IllegalArgumentException if the item is not a written or writable book.
*/
public ItemBuilder bookPage(int page, @NotNull Component content) {
if (this.getType() != Material.WRITTEN_BOOK && this.getType() != Material.WRITABLE_BOOK) {
throw new IllegalArgumentException("bookPage(int, Component) can only be used on WRITTEN_BOOK and WRITABLE_BOOK");
}
BookMeta bookMeta = (BookMeta) this.getItemMeta();
bookMeta.addPages(content);
this.setItemMeta(bookMeta);
return this;
}
/**
* Adds multiple pages to a book item with the specified content.
*
* @param page the page number.
* @param content the content of the pages as Components.
* @return the current ItemBuilder instance.
* @throws IllegalArgumentException if the item is not a written or writable book.
*/
public ItemBuilder bookPage(int page, @NotNull Component... content) {
if (this.getType() != Material.WRITTEN_BOOK && this.getType() != Material.WRITABLE_BOOK) {
throw new IllegalArgumentException("bookPage(int, Component...) can only be used on WRITTEN_BOOK and WRITABLE_BOOK");
}
BookMeta bookMeta = (BookMeta) this.getItemMeta();
bookMeta.addPages(content);
this.setItemMeta(bookMeta);
return this;
}
/**
* Adds multiple pages to a book item with the specified content.
*
* @param page the page number.
* @param content the content of the pages as strings.
* @return the current ItemBuilder instance.
* @throws IllegalArgumentException if the item is not a written or writable book.
*/
public ItemBuilder bookPage(int page, @NotNull String... content) {
if (this.getType() != Material.WRITTEN_BOOK && this.getType() != Material.WRITABLE_BOOK) {
throw new IllegalArgumentException("bookPage(int, String...) can only be used on WRITTEN_BOOK and WRITABLE_BOOK");
}
BookMeta bookMeta = (BookMeta) this.getItemMeta();
bookMeta.addPages(Arrays.stream(content).map(Component::text).toArray(Component[]::new));
this.setItemMeta(bookMeta);
return this;
}
/**
* Sets the generation of a book item.
*
* @param generation the generation of the book.
* @return the current ItemBuilder instance.
* @throws IllegalArgumentException if the item is not a written or writable book.
*/
public ItemBuilder bookGeneration(BookMeta.Generation generation) {
if (this.getType() != Material.WRITTEN_BOOK && this.getType() != Material.WRITABLE_BOOK) {
throw new IllegalArgumentException("bookGeneration(BookMeta.Generation) can only be used on WRITTEN_BOOK and WRITABLE_BOOK");
}
BookMeta bookMeta = (BookMeta) this.getItemMeta();
bookMeta.setGeneration(generation);
this.setItemMeta(bookMeta);
return this;
}
/**
* Adds an NBT tag to the item.
*
* @param key the key of the NBT tag.
* @param type the type of the NBT tag.
* @param value the value of the NBT tag.
* @return the current ItemBuilder instance.
*/
@SuppressWarnings({"rawtypes", "unchecked"})
public ItemBuilder addNBTTag(String key, PersistentDataType type, Object value) {
ItemMeta meta = this.getItemMeta();
meta.getPersistentDataContainer().set(new NamespacedKey("skyblockx", key), type, value);
return this;
}
/**
* Adds an NBT tag to the item, with an option to replace existing tags.
*
* @param key the key of the NBT tag.
* @param type the type of the NBT tag.
* @param value the value of the NBT tag.
* @param replace whether to replace existing tags.
* @return the current ItemBuilder instance.
*/
@SuppressWarnings({"rawtypes", "unchecked"})
public ItemBuilder addNBTTag(String key, PersistentDataType type, Object value, boolean replace) {
ItemMeta meta = this.getItemMeta();
if (replace) {
meta.getPersistentDataContainer().remove(new NamespacedKey("skyblockx", key));
}
meta.getPersistentDataContainer().set(new NamespacedKey("skyblockx", key), type, value);
return this;
}
/**
* Removes an NBT tag from the item.
*
* @param key the key of the NBT tag.
* @return the current ItemBuilder instance.
*/
public ItemBuilder removeNBTTag(String key) {
ItemMeta meta = this.getItemMeta();
meta.getPersistentDataContainer().remove(new NamespacedKey("skyblockx", key));
return this;
}
/**
* Clears all NBT tags from the item.
*
* @return the current ItemBuilder instance.
*/
public ItemBuilder clearNBTTags() {
ItemMeta meta = this.getItemMeta();
meta.getPersistentDataContainer().getKeys().forEach(key -> meta.getPersistentDataContainer().remove(key));
return this;
}
/**
* Checks if the item has an NBT tag with the specified key and type.
*
* @param key the key of the NBT tag.
* @param type the type of the NBT tag.
* @return true if the item has the NBT tag, false otherwise.
*/
@SuppressWarnings({"rawtypes", "unchecked"})
public boolean hasNBTTag(String key, PersistentDataType type) {
return this.getItemMeta().getPersistentDataContainer().has(new NamespacedKey("skyblockx", key), type);
}
/**
* Retrieves the value of an NBT tag with the specified key and type.
*
* @param key the key of the NBT tag.
* @param type the type of the NBT tag.
* @param <T> the type of the value.
* @return the value of the NBT tag.
*/
@SuppressWarnings("unchecked")
public <T> T getNBTTag(String key, PersistentDataType<T, ?> type) {
return (T) this.getItemMeta().getPersistentDataContainer().get(new NamespacedKey("skyblockx", key), type);
}
/**
* Converts the item to a CraftItemStack.
*
* @return the CraftItemStack representation of the item.
*/
public CraftItemStack toCraftItem() {
return CraftItemStack.asCraftCopy(this);
}
/**
* Drops the item at the specified location.
*
* @param location the location to drop the item.
* @return the dropped item.
*/
public Item toItem(Location location) {
Item item = location.getWorld().dropItem(location, this);
item.setPickupDelay(Integer.MAX_VALUE);
return item;
}
/**
* Sets the NMS ItemStack of the item.
*
* @param nmsItemStack the NMS ItemStack.
* @return the current ItemBuilder instance.
*/
public ItemBuilder nmsItemStack(net.minecraft.world.item.ItemStack nmsItemStack) {
this.setItemMeta(CraftItemStack.asBukkitCopy(nmsItemStack).getItemMeta());
return this;
}
/**
* Retrieves the NMS ItemStack of the item.
*
* @return the NMS ItemStack.
*/
public net.minecraft.world.item.ItemStack nmsItemStack() {
return CraftItemStack.asNMSCopy(this);
}
/**
* Retrieves the NMS ItemStack of the item with the specified amount.
*
* @param amount the amount.
* @return the NMS ItemStack.
*/
public net.minecraft.world.item.ItemStack nmsItemStack(int amount) {
net.minecraft.world.item.ItemStack nmsItemStack = CraftItemStack.asNMSCopy(this);
nmsItemStack.setCount(amount);
return nmsItemStack;
}
/**
* Retrieves the NMS ItemStack of the item with the specified amount and damage.
*
* @param amount the amount.
* @param damage the damage value.
* @return the NMS ItemStack.
*/
public net.minecraft.world.item.ItemStack nmsItemStack(int amount, int damage) {
net.minecraft.world.item.ItemStack nmsItemStack = CraftItemStack.asNMSCopy(this);
nmsItemStack.setCount(amount);
nmsItemStack.setDamageValue(damage);
return nmsItemStack;
}
/**
* Sets an NBT tag on the item with the specified key and value.
*
* @param key the key of the NBT tag.
* @param value the value of the NBT tag.
* @return the current ItemBuilder instance.
*/
public ItemBuilder setNMSNBTTag(String key, String value) {
net.minecraft.world.item.ItemStack nmsItemStack = CraftItemStack.asNMSCopy(this);
CompoundTag tag = nmsItemStack.getOrCreateTag();
tag.putString(key, value);
nmsItemStack.setTag(tag);
this.setItemMeta(CraftItemStack.asBukkitCopy(nmsItemStack).getItemMeta());
return this;
}
/**
* Retrieves the value of an NBT tag with the specified key.
*
* @param key the key of the NBT tag.
* @return the value of the NBT tag, or null if not found.
*/
public String getNMSNBTTag(String key) {
net.minecraft.world.item.ItemStack nmsItemStack = CraftItemStack.asNMSCopy(this);
CompoundTag tag = nmsItemStack.getTag();
return tag != null && tag.contains(key) ? tag.getString(key) : null;
}
/**
* Removes an NBT tag with the specified key from the item.
*
* @param key the key of the NBT tag.
* @return the current ItemBuilder instance.
*/
public ItemBuilder removeNMSNBTTag(String key) {
net.minecraft.world.item.ItemStack nmsItemStack = CraftItemStack.asNMSCopy(this);
CompoundTag tag = nmsItemStack.getTag();
if (tag != null) {
tag.remove(key);
nmsItemStack.setTag(tag);
this.setItemMeta(CraftItemStack.asBukkitCopy(nmsItemStack).getItemMeta());
}
return this;
}
/**
* Checks if the item has an NBT tag with the specified key.
*
* @param key the key of the NBT tag.
* @return true if the item has the NBT tag, false otherwise.
*/
public boolean hasNMSNBTTag(String key) {
net.minecraft.world.item.ItemStack nmsItemStack = CraftItemStack.asNMSCopy(this);
CompoundTag tag = nmsItemStack.getTag();
return tag != null && tag.contains(key);
}
/**
* Adds a custom attribute to the item.
*
* @param attributeName the name of the attribute.
* @param value the value of the attribute.
* @param slot the slot where the attribute applies.
* @param operation the operation of the attribute.
* @return the current ItemBuilder instance.
*/
public ItemBuilder addCustomAttribute(String attributeName, double value, String slot, int operation) {
net.minecraft.world.item.ItemStack nmsItemStack = CraftItemStack.asNMSCopy(this);
CompoundTag tag = nmsItemStack.getOrCreateTag();
ListTag attributeModifiers = tag.getList("AttributeModifiers", 10);
CompoundTag attribute = new CompoundTag();
attribute.putString("AttributeName", attributeName);
attribute.putDouble("Amount", value);
attribute.putString("Slot", slot);
attribute.putInt("Operation", operation);
attribute.putUUID("UUID", UUID.randomUUID());
attributeModifiers.add(attribute);
tag.put("AttributeModifiers", attributeModifiers);
nmsItemStack.setTag(tag);
this.setItemMeta(CraftItemStack.asBukkitCopy(nmsItemStack).getItemMeta());
return this;
}
/**
* Retrieves the custom attributes of the item.
*
* @return a list of custom attributes.
*/
public List<CompoundTag> getCustomAttributes() {
net.minecraft.world.item.ItemStack nmsItemStack = CraftItemStack.asNMSCopy(this);
CompoundTag tag = nmsItemStack.getTag();
List<CompoundTag> attributes = new ArrayList<>();
if (tag != null && tag.contains("AttributeModifiers", 9)) {
ListTag attributeModifiers = tag.getList("AttributeModifiers", 10);
for (int i = 0; i < attributeModifiers.size(); i++) {
attributes.add(attributeModifiers.getCompound(i));
}
}
return attributes;
}
/**
* Removes a custom attribute from the item by its name.
*
* @param attributeName the name of the attribute.
* @return the current ItemBuilder instance.
*/
public ItemBuilder removeCustomAttribute(String attributeName) {
net.minecraft.world.item.ItemStack nmsItemStack = CraftItemStack.asNMSCopy(this);
CompoundTag tag = nmsItemStack.getTag();
if (tag != null && tag.contains("AttributeModifiers", 9)) {
ListTag attributeModifiers = tag.getList("AttributeModifiers", 10);
ListTag newAttributeModifiers = new ListTag();
for (int i = 0; i < attributeModifiers.size(); i++) {
CompoundTag attribute = attributeModifiers.getCompound(i);
if (!attribute.getString("AttributeName").equals(attributeName)) {
newAttributeModifiers.add(attribute);
}
}
tag.put("AttributeModifiers", newAttributeModifiers);
nmsItemStack.setTag(tag);
this.setItemMeta(CraftItemStack.asBukkitCopy(nmsItemStack).getItemMeta());
}
return this;
}
/**
* Clones the itemBuilder.
*
* @return the cloned itemBuilder.
*/
@Override
public @NotNull ItemStack clone() {
ItemStack cloned = super.clone();
return new ItemBuilder(cloned);
}
/**
* Clears the meta of the item.
* @return the current ItemBuilder instance.
*/
public ItemBuilder clearMeta() {
this.setItemMeta(Bukkit.getItemFactory().getItemMeta(this.getType()));
return this;
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment