Jump to content

1.19 I need help getting my tags to work


JoachimTa

Recommended Posts

I am making a mod where when you kill a mob you get its hp into soulpower, and I am trying to get it to be stored in a nbt tag on the enchanted weapon, everything works except the nbt Tag.

I have tried with setTags but that gets rid of the enchantment.
 

Spoiler
package com.pizzacat.soulmod.enchantment;

import net.minecraft.nbt.CompoundTag;
import net.minecraft.world.entity.EquipmentSlot;
import net.minecraft.world.item.enchantment.Enchantment;
import net.minecraft.world.item.enchantment.EnchantmentCategory;
import net.minecraftforge.event.entity.living.LivingDeathEvent;
import net.minecraftforge.eventbus.api.SubscribeEvent;
import net.minecraftforge.fml.common.Mod;

@Mod.EventBusSubscriber
public class SoulStealEnchantment extends Enchantment {
    protected SoulStealEnchantment(Rarity pRarity, EnchantmentCategory pCategory, EquipmentSlot... pSlots) {
        super(pRarity, pCategory, pSlots);
    }

    static float soulpower;
    static float sp;

    public static CompoundTag storeSoulPower() {
        soulpower += sp;
        if(soulpower > 1000){
            soulpower = 1000;
        }
        CompoundTag nbtData = new CompoundTag();
        nbtData.putString(String.valueOf(soulpower), "/1000");
        return nbtData;
    }

    @SubscribeEvent
    public static void onPlayerKill(LivingDeathEvent entity){
        entity.getEntity().getLevel();
        if(entity.getEntity().level.isClientSide()){
            boolean playerKill = SoulStealEvent.playerKill;
            int level = SoulStealEvent.level;
            if(level == 1 && playerKill == true) {
                sp = entity.getEntity().getMaxHealth();
                storeSoulPower();
                sp = 0;
            }
        }
    }

    @Override
    public int getMaxLevel() {
        return 1;
    }

}

 

Spoiler
package com.pizzacat.soulmod.enchantment;

import net.minecraft.nbt.CompoundTag;
import net.minecraft.world.damagesource.DamageSource;
import net.minecraft.world.entity.player.Player;
import net.minecraft.world.item.ItemStack;
import net.minecraft.world.item.enchantment.EnchantmentHelper;
import net.minecraftforge.event.entity.living.LivingDeathEvent;
import net.minecraftforge.event.entity.living.LivingEquipmentChangeEvent;
import net.minecraftforge.eventbus.api.SubscribeEvent;
import net.minecraftforge.fml.common.Mod;

@Mod.EventBusSubscriber
public class SoulStealEvent {

    static boolean playerKill;
    static int level;
    static ItemStack soulStealWeapon;

    @SubscribeEvent
    public static void onLivingDeath(LivingDeathEvent entity){
        entity.getEntity().getLevel();
        DamageSource source = entity.getSource();
        if(source.getEntity() instanceof Player) {
            playerKill = true;
        }
    }

    @SubscribeEvent
    public static void onEquipChange(LivingEquipmentChangeEvent equipment){
        ItemStack mainHandItem = equipment.getEntity().getMainHandItem();
        level = EnchantmentHelper.getItemEnchantmentLevel(ModEnchantments.SOUL_STEAL.get(), mainHandItem);
        if(level == 1){
            soulStealWeapon = mainHandItem;
        }
    }

}

 

 

Link to comment
Share on other sites

4 hours ago, Luis_ST said:

You can not store data like this in your Enchantment and Event class.
If you want to store the data you need to use CompoundTag or a Capability (last one is recommended).

How do I do this?, I am very new to modding in minecraft, and aren't I usign compoundTag or do I need to do it in another class?

Link to comment
Share on other sites

2 hours ago, JoachimTa said:

How do I do this?, I am very new to modding in minecraft, and aren't I usign compoundTag or do I need to do it in another class?

Yeah but not how you should do it, but i would highly recommend you to use a Capability.
CompoundTag should be used to store and load data and not on runtime.

Edited by Luis_ST
Link to comment
Share on other sites

9 minutes ago, Luis_ST said:

Yeah but not how you should do it, but i would highly recommend you to use a Capability.
CompoundTag should be used to store and load data and not on runtime.

Yeah, but I am trying to make so that it saves the entitys hp on the sword, so you can see it, should I not use nbt tags for it or?

Link to comment
Share on other sites

8 minutes ago, Luis_ST said:

Do you want to display the tooltip for all Items or only for your Mods Items?

So when I kill a mob, its hp becomes a value i call soulpower, and that value is gonna be displayed on the weapon I killed it with that has the soul steal enchantment. Its gonna be displayed when I hover over my mouse on the sword in my inventory. All items with the soul steal enchantment is gonna have its own separate value based on how many mobs it has killed

Edited by JoachimTa
Link to comment
Share on other sites

I've split your purpose in two parts:

  1. Adding the CompoundTag
    First of all call ItemStack#getOrCreateTagElement with your Mod id, then add to the CompoundTag add data you want to add
    In your case CompoundTag#putInt the first parameter is the key the second the value
  2. Add the CompoundTag to the Tooltip of the Item
    Subscribe to ItemTooltipEvent, from the Event you can get the ItemStack,
    check if the ItemStack has your Enchantment and check if the ItemStack has your Tag using a non ull check on ItemStack#getTagElement with your Mod id.
    Then read the value from the CompoundTag via #getInt with the key you used in #putInt.
    After that create a new Component via Component#literal with your value and add this Component to the tooltip list of the Event
Link to comment
Share on other sites

27 minutes ago, JoachimTa said:
  Reveal hidden contents
public static CompoundTag soulStealCompoundTag(){
        ItemStack stack;
        new ItemStack().getOrCreateTag(soulmod.MODID);
    }

 

Did you mean something like this?

Spoiler
    public static CompoundTag soulStealCompoundTag(){
        CompoundTag tag = ItemStack.of(new CompoundTag()).getOrCreateTagElement(soulmod.MODID);
        tag.putFloat(soulmod.MODID, soulpower);
        return null;
    }

 

This is what I have done, I don't know if this was what you meant

Link to comment
Share on other sites

4 hours ago, JoachimTa said:

Sorry I dont understand, What does # mean, and how do I call ItemStack with getOrCreateTagElement.

The # is a sign that the following "name" is a non-static method or non-static field in the class, which you need to call.

3 hours ago, JoachimTa said:
CompoundTag tag = ItemStack.of(new CompoundTag()).getOrCreateTagElement(soulmod.MODID);

Why did you create there a new ItemStack with an Empty CompoundTag?
You should use the ItemStack on which you checked if your enchantment is preset (level > 0).

Do you know basic java?

Link to comment
Share on other sites

2 minutes ago, Luis_ST said:

The # is a sign that the following "name" is a non-static method or non-static field in the class, which you need to call.

Why did you create there a new ItemStack with an Empty CompoundTag?
You should use the ItemStack on which you checked if your enchantment is preset (level > 0).

Do you know basic java?

Yes, but I dont know how this ItemStack thing works, so i dont know what to put in the parantheses

Link to comment
Share on other sites

14 hours ago, Luis_ST said:

Adding the CompoundTag
First of all call ItemStack#getOrCreateTagElement with your Mod id, then add to the CompoundTag add data you want to add
In your case CompoundTag#putFloat the first parameter is the key the second the value

If you done step 1 you can continue with step 2:

14 hours ago, Luis_ST said:

Add the CompoundTag to the Tooltip of the Item
Subscribe to ItemTooltipEvent, from the Event you can get the ItemStack,
check if the ItemStack has your Enchantment and check if the ItemStack has your Tag using a non ull check on ItemStack#getTagElement with your Mod id.
Then read the value from the CompoundTag via #getFloat with the key you used in #putFloat.
After that create a new Component via Component#literal with your value and add this Component to the tooltip list of the Event

Link to comment
Share on other sites

this is what I understood, the Item gets checked for my enchantment before arriving so it only needs to be checked for the tag here. I dont understand the component.literal part?

Spoiler

 

    @SubscribeEvent
    public static ItemTooltipEvent tooltip(){
        if (soulStealWeapon.getTagElement(soulmod.MODID) != null) {
            soulStealCompoundTag().getFloat(soulmod.MODID);
            Component.literal(soulpower?)
        }
    }

 

 

Edited by JoachimTa
Link to comment
Share on other sites

Update: is this what you wanted?

Spoiler
   @SubscribeEvent
    public static ItemTooltipEvent tooltip(){
        if (soulStealWeapon.getTagElement(soulmod.MODID) != null) {
            soulStealCompoundTag().getFloat(soulmod.MODID);
             Component component = new Component() {
                 @Override
                 public Style getStyle() {
                     return null;
                 }

                 @Override
                 public ComponentContents getContents() {
                     return null;
                 }

                 @Override
                 public List<Component> getSiblings() {
                     return null;
                 }

                 @Override
                 public FormattedCharSequence getVisualOrderText() {
                     return null;
                 }
             };
        }
        return null;
    }

 

 

Link to comment
Share on other sites

Quote

@SubscribeEvent

public static ItemTooltipEvent tooltip(){

This makes no sense.

Event handlers are consumers of events (in their parameters), they don't create/supply them.

Boilerplate:

If you don't post your logs/debug.log we can't help you. For curseforge you need to enable the forge debug.log in its minecraft settings. You should also post your crash report if you have one.

If there is no error in the log file and you don't have a crash report then post the launcher_log.txt from the minecraft folder. Again for curseforge this will be in your curseforge/minecraft/Install

Large files should be posted to a file sharing site like https://gist.github.com  You should also read the support forum sticky post.

Link to comment
Share on other sites

1 minute ago, diesieben07 said:

No shit... Show it. We have no idea what it does.

Spoiler
public static CompoundTag soulStealCompoundTag(){
        CompoundTag tag = ItemStack.of(new CompoundTag()).getOrCreateTagElement(soulmod.MODID);
        tag.putFloat(soulmod.MODID, soulpower);
        return null;
    }

 

 

Link to comment
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Unfortunately, your content contains terms that we do not allow. Please edit your content to remove the highlighted words below.
Reply to this topic...

×   Pasted as rich text.   Restore formatting

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

Announcements



  • Recently Browsing

    • No registered users viewing this page.
  • Posts

    • Hello! I'm trying to get a list of all entries registered in the infusion upgrade registry. Code can be found in github: https://github.com/ChamoisEST/MiningMadness/tree/1.20.1 Registry in common/registries/MMRegistries.java Event that calls the registry is in MiningMadness.java List of registered entries should be called in common/capabilities/infusion/InfusionCapabilityImplementation.java:getActiveInfusions() in the for loop. Is there any way to accomplish that? Thanks in advance!  
    • So, I am trying to create and add tags to my custom damage type, but looks like I made something wrong, since it crashing with error that "cannot register" damage type. Im trying to register it, and in datagen add tags, but it everytime crashing due to not register "grimtales:entropy". Full code there - https://github.com/undertakerJ/Grim-Tales-Forge ModDamageTypes class public class ModDamageTypes { public static final DeferredRegister<DamageType> DAMAGE_TYPES = DeferredRegister.create(Registries.DAMAGE_TYPE, GrimTales.MOD_ID); public static final ResourceKey<DamageType> ENTROPY_KEY = ResourceKey.create(Registries.DAMAGE_TYPE, new ResourceLocation(GrimTales.MOD_ID, "entropy")); public static final RegistryObject<DamageType> ENTROPY = DAMAGE_TYPES.register( "entropy", () -> new DamageType("entropy_effect", DamageScaling.ALWAYS, 1f, DamageEffects.HURT)); // // public static final DamageSource ENTROPY_SOURCE = new DamageSource(Holder.direct(ENTROPY.get())); public static void register(IEventBus eventBus) { DAMAGE_TYPES.register(eventBus); } } Datagen for damageTags public class ModDamageTagsProvider extends DamageTypeTagsProvider { public ModDamageTagsProvider( PackOutput p_270719_, CompletableFuture<HolderLookup.Provider> p_270256_, @Nullable ExistingFileHelper existingFileHelper) { super(p_270719_, p_270256_, GrimTales.MOD_ID, existingFileHelper); } @Override protected void addTags(HolderLookup.Provider pProvider) { this.tag(DamageTypeTags.BYPASSES_INVULNERABILITY).add(ModDamageTypes.ENTROPY_KEY); } } Datagen class it self   @Mod.EventBusSubscriber(modid = GrimTales.MOD_ID, bus = Mod.EventBusSubscriber.Bus.MOD) public class DataGenerators { @SubscribeEvent public static void gatherData(GatherDataEvent event){ DataGenerator generator = event.getGenerator(); PackOutput packOutput = generator.getPackOutput(); ExistingFileHelper helper = event.getExistingFileHelper(); CompletableFuture<HolderLookup.Provider> lookupProvider = event.getLookupProvider(); generator.addProvider(event.includeServer(), new ModDamageTagsProvider(packOutput, lookupProvider, helper)); } } And register class in main class public GrimTales() { IEventBus modEventBus = FMLJavaModLoadingContext.get().getModEventBus(); ModDamageTypes.register(modEventBus); modEventBus.addListener(this::commonSetup); MinecraftForge.EVENT_BUS.register(this); modEventBus.addListener(this::addCreative); }  
    • Looking for a semi-vanilla Minecraft server? Maybe one with keep inventory and land claims? I have one for you! Let me introduce you to Safe Survival! Come on and join us at mc.safesurvival.net. It is bedrock supported too!
    • Hi. I'm trying to play RLCraft with Optifine but my game keeps crashing on startup with Exit Code 1. The modpack was working fine yesterday, not sure what changed to make it not wanna work anymore. I was hoping someone here could help me figure out what's going wrong. If I remove Optifine, nothing changes, I still get the same errors. Thanks in advance. Crash Report (I only included the errors+fatal, I’m not sure if more is needed, please let me know): https://pastebin.ai/66ivknz0f4  
    • I am trying to port my mod from 1.20.2 to 1.21, but I am encountering difficulties regarding the classes for rendering the GUI and related events. What are the equivalents of the following classes? net.minecraftforge.client.event.RenderGuiOverlayEvent net.minecraftforge.client.gui.overlay.NamedGuiOverlay net.minecraftforge.client.gui.overlay.ForgeGui net.minecraftforge.client.gui.overlay.GuiOverlayManager net.minecraftforge.client.gui.overlay.IGuiOverlay   thx
  • Topics

×
×
  • Create New...

Important Information

By using this site, you agree to our Terms of Use.