Помогите Как работать с классом -> NBTTagCompound [Решено]

Статус
Закрыто для дальнейших ответов.
Как бы мы таким образом записывает на предмет craft тэг nbt, а далее можем способом выше сделать из него обычный предмет и дать игроку

Глаза разуй, тебе три человека об этом писали


Спринти... Так что всё же, что я должен был найти?
видимо имеется ввиду вывод тега в консоль\игроку
 
Короче твой касяк в том, что сперва идет tag в нем display и потом уже Lore tag:{display:{Lore:[0:"test"]}}
Окей.
Представим что тэг teg мы получаем сразу с предмета.
Далее на нужно в него поместить тэг под именем display, а потом уже на display цеплять Lore ?
 
Окей.
Представим что тэг teg мы получаем сразу с предмета.
Далее на нужно в него поместить тэг под именем display, а потом уже на display цеплять Lore ?
Сперва проверяешь на наличие tag, если нет создаешь пустой тег, потом проверяешль display, та же операция что и с tag, дальше проверяешь наличие Lore, если есть, дописываешь-заменяешь, если нет, создаешь новый.
Вот такую шапку делаешь короче.

NBTTagCompound nbt = new NBTTagCompound();
NBTTagCompound tag = new NBTTagCompound();
NBTTagCompound display = new NBTTagCompound();
NBTTagList Lore = new NBTTagList();
CraftItemStack.asNMSCopy(e.getPlayer().getInventory().getItemInMainHand()).save(nbt);
if(!nbt.hasKey("tag")) nbt.set("tag", tag);
tag = (NBTTagCompound) nbt.get("tag");
if(!tag.hasKey("display")) tag.set("display", display);
display = (NBTTagCompound) tag.get("display");
if(!display.hasKey("Lore")) display.set("Lore", Lore);
Lore = (NBTTagList) display.get("Lore");

Дальше уже работаешь с лором.
 
Последнее редактирование:
Ураааа, заработало) Благодаря вам всем, теперь и мне известна это магия с тэгами)
Всем спасибо за помощь. С новыми знаниями попробую решить старую проблему (тема Lore) которая.
Вот если чё рабочий полный метод))
Java:
    private void test(Player p) {
      
        NBTTagCompound nbt = new NBTTagCompound();
        NBTTagCompound tag = new NBTTagCompound();
        NBTTagCompound display = new NBTTagCompound();
        NBTTagList Lore = new NBTTagList();
        Lore.add(new NBTTagString("", "THIS TEST1"));
        Lore.add(new NBTTagString("", "THIS TEST2"));
        Lore.add(new NBTTagString("", "THIS TEST3"));
      
        CraftItemStack stack = this.getCraftVersion(p.getItemInHand());
        CraftItemStack.asNMSCopy(stack).save(nbt);
        //CraftItemStack.asNMSCopy(p.getItemInHand()).save(nbt);

        if (!nbt.hasKey("tag")) {
            nbt.set("tag", tag);
        }
      
        tag = (NBTTagCompound) nbt.get("tag");
        if (!tag.hasKey("display")) {
            tag.set("display", display);
        }
      
        display = (NBTTagCompound) tag.get("display");
        if (!display.hasKey("Lore")) {
            display.set("Lore", Lore);
        }

        //Lore = (NBTTagList) display.get("Lore");
        ItemStack i = CraftItemStack.asBukkitCopy(net.minecraft.server.v1_6_R3.ItemStack.createStack(nbt));
        p.getInventory().addItem(i);
    }

А вот запись тега(Ключ = Произвольная строка, Значение = Ник игрока) без замены предмета, но нужен слот инвентаря:
Java:
    public static void setTag(Player player, int slot, String tag) {
        if (player instanceof CraftPlayer) {
            net.minecraft.server.v1_7_R4.ItemStack nmsStack = (((CraftPlayer) player).getHandle()).inventory.getItem(slot);
            if (nmsStack != null)
                if (nmsStack.hasTag()) {
                    nmsStack.getTag().setString(tag, player.getName());
                } else {
                    nmsStack.setTag(new NBTTagCompound());
                    nmsStack.getTag().setString(tag, player.getName());
                }
        }
    }
Всё же мне пригодился вот такой способ, но при его тестировании оказалось, что он не работает.
После первого hasTag(); == понятно что false, ладно. Создали. Но после вызова этой функции с тем же предметом в руке, он всё равно игнорит, что мгновение назад Tag был ему установлен. В чём ошибка?
Java:
            net.minecraft.server.v1_6_R3.ItemStack stack = CraftItemStack.asNMSCopy(weapon);

            if (stack != null) {
                if (stack.hasTag()) {
                    Bukkit.broadcastMessage("Есть ТАГ");
                } else {
                    Bukkit.broadcastMessage("Нет ТАГа");
                    stack.setTag(new NBTTagCompound());
                    stack.getTag().setString("TEST", "PROST");
                }
            }
 
Ураааа, заработало) Благодаря вам всем, теперь и мне известна это магия с тэгами)
Всем спасибо за помощь. С новыми знаниями попробую решить старую проблему (тема Lore) которая.
Вот если чё рабочий полный метод))
Java:
    private void test(Player p) {
     
        NBTTagCompound nbt = new NBTTagCompound();
        NBTTagCompound tag = new NBTTagCompound();
        NBTTagCompound display = new NBTTagCompound();
        NBTTagList Lore = new NBTTagList();
        Lore.add(new NBTTagString("", "THIS TEST1"));
        Lore.add(new NBTTagString("", "THIS TEST2"));
        Lore.add(new NBTTagString("", "THIS TEST3"));
     
        CraftItemStack stack = this.getCraftVersion(p.getItemInHand());
        CraftItemStack.asNMSCopy(stack).save(nbt);
        //CraftItemStack.asNMSCopy(p.getItemInHand()).save(nbt);

        if (!nbt.hasKey("tag")) {
            nbt.set("tag", tag);
        }
     
        tag = (NBTTagCompound) nbt.get("tag");
        if (!tag.hasKey("display")) {
            tag.set("display", display);
        }
     
        display = (NBTTagCompound) tag.get("display");
        if (!display.hasKey("Lore")) {
            display.set("Lore", Lore);
        }

        //Lore = (NBTTagList) display.get("Lore");
        ItemStack i = CraftItemStack.asBukkitCopy(net.minecraft.server.v1_6_R3.ItemStack.createStack(nbt));
        p.getInventory().addItem(i);
    }


Всё же мне пригодился вот такой способ, но при его тестировании оказалось, что он не работает.
После первого hasTag(); == понятно что false, ладно. Создали. Но после вызова этой функции с тем же предметом в руке, он всё равно игнорит, что мгновение назад Tag был ему установлен. В чём ошибка?
Java:
            net.minecraft.server.v1_6_R3.ItemStack stack = CraftItemStack.asNMSCopy(weapon);

            if (stack != null) {
                if (stack.hasTag()) {
                    Bukkit.broadcastMessage("Есть ТАГ");
                } else {
                    Bukkit.broadcastMessage("Нет ТАГа");
                    stack.setTag(new NBTTagCompound());
                    stack.getTag().setString("TEST", "PROST");
                }
            }
Так ты его выдай в руку обратно.
 
Так ты его выдай в руку обратно.
А я по какой то причине подумал, что данный кусок кода может без перевыдачи заменять данные.
Прост представьте случай, что игрок будет стрелять с прицелом, убьёт моба и прицел сам выключится.
Или во время перестрелки убив одного игрока, то снова прицел вырубится из-за перевыдачи оружия.
Ладно, пойду пробовать.
 
Так ты его выдай в руку обратно.
Особенность этого метода в том, что заменять предметы не нужно.Зная слот в инвентаре можно взаимодействовать с нбт тегами без замены предмета, напрямую.
 
Особенность этого метода в том, что заменять предметы не нужно.Зная слот в инвентаре можно взаимодействовать с нбт тегами без замены предмета, напрямую.
Так почему же тогда не работает?
 
Что в ссылке weapon?
V2VK9q7txGMg1A.png
 
Я подумал ты в общем, сможешь ли получить тег, получить сможешь да.Но способ работать не будет, я для этого специально и заметил, что нужен слот.Возможно, можно переделать и без слота, но я пока не пытался.
 
Я подумал ты в общем, сможешь ли получить тег, получить сможешь да.Но способ работать не будет, я для этого специально и заметил, что нужен слот.Возможно, можно переделать и без слота, но я пока не пытался.
Окей, а не подскажите тогда способ, как можно получить слот предмета в руке?
 
Окей, а не подскажите тогда способ, как можно получить слот предмета в руке?
Сходу не вспомню, но как минимум, банальным перебором и сравнением текущего предмета с уникальными атрибутами предмета в руке.Может кто штатный способ знает?
 
player.getInventory().getHeldItemSlot()
 
Я подумал ты в общем, сможешь ли получить тег, получить сможешь да.Но способ работать не будет, я для этого специально и заметил, что нужен слот.Возможно, можно переделать и без слота, но я пока не пытался.
Вот Blc_Dragon подсказал как и да, действительно, так установился. =)
Пошёл делать дальше.
Рабочий варик:
Java:
int slot = p.getInventory().getHeldItemSlot();
net.minecraft.server.v1_6_R3.ItemStack stack = (((CraftPlayer) p).getHandle()).inventory.getItem(slot);
 
Последнее редактирование:
TRIGGERED

Я BLC (сокращение от black)
Соре, с уважением
Собственно проблема в следующем.
Есть 2 метода. Как бы... всё работает и первый Lore успешно ставится. Никаких ошибок в консоль не кидает.
Вместе с Lore я в tag записываю ещё кол-во убитых игроков и npc. Когда приходит время из tag взять данные по убийству игроков или npc, то он говорит что всё по нулям. В чём ошибка понять не могу...
P.S. Если есть ошибки то поправьте пожалуйста, как вы поняли работаю с этим впервой)

Изначально метод вызывается проверочной командой и переменная isPlayerKill = true;
Компоненты tag, display и lore объявлены выше методов (забыл как правильно это называется).

Java:
public void addKillWeapon(Player killer, boolean isPlayerKill) {

        int slot = killer.getInventory().getHeldItemSlot();
        ItemStack weapon = killer.getItemInHand();

        if (weapon.getType() != AIR) {

            net.minecraft.server.v1_6_R3.ItemStack stack = (((CraftPlayer) killer).getHandle()).inventory.getItem(slot);

            if (stack != null) {

                if (stack.hasTag()) {

                    Bukkit.broadcastMessage("Таг уже был!");
                    tag = stack.getTag();

                    if (tag.hasKey("display")) {

                        display = (NBTTagCompound) tag.get("display");
                        int playerkill = tag.getInt("PlayersKilled");
                        int npckill = tag.getInt("NpcKilled");

                        Bukkit.broadcastMessage("playerkill: " + playerkill);
                        Bukkit.broadcastMessage("npckill: " + npckill);
                        lore = new NBTTagList();

                        if (isPlayerKill) {
                            playerkill++;
                            lore.add(new NBTTagString("", LORE_KILL_PLAYER + playerkill));
                            lore.add(new NBTTagString("", LORE_KILL_NPC + npckill));
                            tag.setInt("PlayersKilled", playerkill);
                        } else {
                            npckill++;
                            lore.add(new NBTTagString("", LORE_KILL_PLAYER + playerkill));
                            lore.add(new NBTTagString("", LORE_KILL_NPC + npckill));
                            tag.setInt("NpcKilled", npckill);
                        }

                        display.set("Lore", lore);
                        stack.setTag(tag);
                    } else {
                        Bukkit.broadcastMessage("Таг был, но не полный!");
                        setFirstLore(false, isPlayerKill);
                        stack.setTag(tag);
                    }

                } else {
                    Bukkit.broadcastMessage("Таг не было!");
                    setFirstLore(true, isPlayerKill);
                    stack.setTag(tag);
                }
            }
        }
    }

    private void setFirstLore(boolean isNewTag, boolean isPlayerKill) {
        Bukkit.broadcastMessage("Ставлю первый ЛОРЕ");

        if (isNewTag) {
            tag = new NBTTagCompound();
        }

        if (!tag.hasKey("display")) {
            display = new NBTTagCompound();
            tag.set("display", display);
        }

        display = (NBTTagCompound) tag.get("display");
        if (!display.hasKey("Lore")) {
            lore = new NBTTagList();
            if (isPlayerKill) {
                lore.add(new NBTTagString("", LORE_KILL_PLAYER + 1));
                lore.add(new NBTTagString("", LORE_KILL_NPC + 0));
                tag.setInt("PlayersKilled", 1);
                tag.setInt("NpcKilled", 0);
            } else {
                lore.add(new NBTTagString("", LORE_KILL_PLAYER + 0));
                lore.add(new NBTTagString("", LORE_KILL_NPC + 1));
                tag.setInt("PlayersKilled", 0);
                tag.setInt("NpcKilled", 1);
            }
            display.set("Lore", lore);
        }
    }
 
Соре, с уважением
Собственно проблема в следующем.
Есть 2 метода. Как бы... всё работает и первый Lore успешно ставится. Никаких ошибок в консоль не кидает.
Вместе с Lore я в tag записываю ещё кол-во убитых игроков и npc. Когда приходит время из tag взять данные по убийству игроков или npc, то он говорит что всё по нулям. В чём ошибка понять не могу...
P.S. Если есть ошибки то поправьте пожалуйста, как вы поняли работаю с этим впервой)

Изначально метод вызывается проверочной командой и переменная isPlayerKill = true;
Компоненты tag, display и lore объявлены выше методов (забыл как правильно это называется).

Java:
public void addKillWeapon(Player killer, boolean isPlayerKill) {

        int slot = killer.getInventory().getHeldItemSlot();
        ItemStack weapon = killer.getItemInHand();

        if (weapon.getType() != AIR) {

            net.minecraft.server.v1_6_R3.ItemStack stack = (((CraftPlayer) killer).getHandle()).inventory.getItem(slot);

            if (stack != null) {

                if (stack.hasTag()) {

                    Bukkit.broadcastMessage("Таг уже был!");
                    tag = stack.getTag();

                    if (tag.hasKey("display")) {

                        display = (NBTTagCompound) tag.get("display");
                        int playerkill = tag.getInt("PlayersKilled");
                        int npckill = tag.getInt("NpcKilled");

                        Bukkit.broadcastMessage("playerkill: " + playerkill);
                        Bukkit.broadcastMessage("npckill: " + npckill);
                        lore = new NBTTagList();

                        if (isPlayerKill) {
                            playerkill++;
                            lore.add(new NBTTagString("", LORE_KILL_PLAYER + playerkill));
                            lore.add(new NBTTagString("", LORE_KILL_NPC + npckill));
                            tag.setInt("PlayersKilled", playerkill);
                        } else {
                            npckill++;
                            lore.add(new NBTTagString("", LORE_KILL_PLAYER + playerkill));
                            lore.add(new NBTTagString("", LORE_KILL_NPC + npckill));
                            tag.setInt("NpcKilled", npckill);
                        }

                        display.set("Lore", lore);
                        stack.setTag(tag);
                    } else {
                        Bukkit.broadcastMessage("Таг был, но не полный!");
                        setFirstLore(false, isPlayerKill);
                        stack.setTag(tag);
                    }

                } else {
                    Bukkit.broadcastMessage("Таг не было!");
                    setFirstLore(true, isPlayerKill);
                    stack.setTag(tag);
                }
            }
        }
    }

    private void setFirstLore(boolean isNewTag, boolean isPlayerKill) {
        Bukkit.broadcastMessage("Ставлю первый ЛОРЕ");

        if (isNewTag) {
            tag = new NBTTagCompound();
        }

        if (!tag.hasKey("display")) {
            display = new NBTTagCompound();
            tag.set("display", display);
        }

        display = (NBTTagCompound) tag.get("display");
        if (!display.hasKey("Lore")) {
            lore = new NBTTagList();
            if (isPlayerKill) {
                lore.add(new NBTTagString("", LORE_KILL_PLAYER + 1));
                lore.add(new NBTTagString("", LORE_KILL_NPC + 0));
                tag.setInt("PlayersKilled", 1);
                tag.setInt("NpcKilled", 0);
            } else {
                lore.add(new NBTTagString("", LORE_KILL_PLAYER + 0));
                lore.add(new NBTTagString("", LORE_KILL_NPC + 1));
                tag.setInt("PlayersKilled", 0);
                tag.setInt("NpcKilled", 1);
            }
            display.set("Lore", lore);
        }
    }
возможно ты двигаешь айтем в инвентаре в режиме креатива. в этом случае кастомные тэги стираются.
 
Статус
Закрыто для дальнейших ответов.
Назад
Верх