Question about Addon Development
WolfieWaffle opened this issue ยท 15 comments
I am trying to create an addon for Blood Magic to make it more dangerous to use. I want it so that once the player starts using Blood Magic, say maybe once you have any blood in Soul network, your LP starts to drain at a slow passive rate, and you will have major consequences if you reach 0.
My question is about how Blood Magic is set up. I'm still relatively new to modding, but I understand OOP well enough, so I wanted to know how Blood Magic works in the broad sense.
First of all, is this possible with your current setup? Is this a possible addon to make?
Secondly, if so where do you store LP and how to you modify it. Is it player NBT, is there some class per world that handles all of it?
And finally, how would I mark a player as 'has started Blood Magic' so that I know when to start draining LP?
I hope I have done this right, I'm not exactly sure where to as these types of questions but good luck o further development.
Yes, this is very possible.
To get a player's LP network, use NetworkHelper.getSoulNetwork(EntityPlayer)
. This will provide a SoulNetwork for the given player.
To check if a player has started using Blood Magic, use SoulNetwork#getOrbTier() > 0
.
OK, thanks, that's easier than I thought. My only question is what NetworkHelper instance do I use? Is there one per world, or do I have to pass it in with a constructor, or can I just create a new instance in the class I use?
Huh, okay. So I guess I can just call it? Ohh, and I assume the static class can access what world it was called from, and therefore the world the player is in. I'm still getting used to the structure OOP programs, interesting. Thanks for the help! I'll post here if I run into further issues but I think I can figure the rest out.
Ohh, and I assume the static class can access what world it was called from, and therefore the world the player is in.
A world is not needed. It just pulls an arbitrary world and uses that. The world doesn't matter since we save our data globally instead of per-world.
OK, I was planning on having each player have logic done at the same time, but really it doesn't matter. So using PlayerTickEvent
only applies once, and I assume Minecraft or Forge handles the delta. But what do you mean by use the ones the network provides? I can only see NetworkHelper.getSoulNetwork(event.player)
I tried using these methods, but It doesn't seem to drain any LP and the orb tier seems to keep resetting to 0. Do you know what I am doing wrong?
Also that is not the event to use for that. WorldTickEvent
fires every tick for every world. In vanilla, this would mean 3 times per tick. On top of that, you're needlessly iterating over all the players. 3 times per tick. The correct way to do this would be to use PlayerTickEvent
.
so something like
@Mod.EventBusSubscriber
public class Handler {
@SubscribeEvent
public static void tick(TickEvent.PlayerTickEvent event) {
// Get network
SoulNetwork network = NetworkHelper.getSoulNetwork(event.player);
// Debug
System.out.println(network.getOrbTier());
System.out.println(network.getCurrentEssence());
// Drain Life
if (network.getOrbTier() > 1) {
network.syphonAndDamage(network.getPlayer(), 1);
}
}
}
This seems to not do anything either, instead it seems to just give me 200 LP whenever I right click with a blood orb, which is confusing because I don't even have 100 or 200 in this code. Is that a default feature?
EDIT: Derp, just saw that the orbTier was checking for > 1. I'll change that real quick and see if it works.
it seems to just give me 200 LP whenever I right click with a blood orb, which is confusing because I don't even have 100 or 200 in this code. Is that a default feature?
That's uh... Basic Blood Magic... Have you never actually played BM?
I thought I had... but isn't that infinite LP? Maybe I was in creative.
Either way, I think it's mostly working, I have this code:
@Mod.EventBusSubscriber
public class Handler {
// This annotation and parameter catch the event
@SubscribeEvent
public static void tick(TickEvent.PlayerTickEvent event) {
// Get network
SoulNetwork network = NetworkHelper.getSoulNetwork(event.player);
// Debug
System.out.println(network.getOrbTier());
System.out.println(network.getCurrentEssence());
// Drain Life
if (network.getOrbTier() > 0 && !event.player.worldObj.isRemote) {
if (event.player.worldObj.getTotalWorldTime() % 10 == 0) {
network.syphonAndDamage(network.getPlayer(), 1);
}
}
}
}
It now works pretty much as intended, but it takes 2 LP each cycle instead of 1, and I don't think the period of the cycle is consistent. But I think these are not on this BM side, so I think all my questions in this area are answered, but I wanted to make sure if this is some Blood Magic thing or just some error in my generic code, which I think is most likely.