tModLoader

tModLoader

Block's Boss Bars
 This topic has been pinned, so it's probably important
BlockCrusader  [developer] 23 Apr, 2024 @ 3:03pm
Mod.Call Guide
Mod.Call Guide
Does a boss in your mod have special logic for its health display (and/or a shield display)? By default, this mod isn't able to pick up on such logic, but with a Mod.Call you can implement it to the boss bar added by this mod.

This thread will walk you through each of the arguments you must provide when making a Call to this mod.

Getting started
First, you'll need to know how make a Call in general; this guide on the tML GitHub[github.com] can help.

You should place your call in the PostSetupContent() hook of a ModSystem class.

Many of the arguments in this call are methods, so make sure you have a place for those. The same ModSystem class you place your Call in should suffice.

Don't forget to check that this mod is loaded (its internal name is 'BBossBars') before attempting to make the Call. You can use this example code below;
if (ModLoader.TryGetMod("BBossBars", out Mod bossBarMod)) { // Mod.Call code goes here }

The Call
The call you'll make requires 9-10 arguments, seven of which are methods. Here is a full example (Excluding the optional isMiniboss argument), from my mod Corruption Core Boss (Notice the methods are not invoked);
bossBarMod.Call("AddCustomBarLogic", ModContent.NPCType<CoreBoss>(), BBossBarGetAssociatedNPCs, BBossBarGetHP, BBossBarGetMaxHP, BBossBarGetShield, BBossBarGetMaxShield, BBossBarGetIcon, BBossBarGetText );
The above code doesn't make much sense without context; from here, each of the arguments will be detailed.


0: CallName
This argument is a string

Call Name is simply the name of the call being made. In this case it will always be "AddCustomBarLogic", since that is the only call in Block's Boss Bars.


1: NpcType
This argument is a int

This should be NPC.type of the boss your logic is for. To retrive the type of a modded NPC, use 'ModContent.NPCType<ModNpcHere>()', where ModNpcHere is the class name of your NPC.



The rest of the arguments are all functions. They will all take an int (but their return type varies).
The given int is the NPC.whoAmI of the NPC who is having a boss bar drawn. It will always be of the NPC.type you specify in the NPC type argument. To get the associated NPC instance, use code such as 'NPC nPC = Main.npc[intWhoAmI]', where intWhoAmI is the given int.



2: GetAssociatedNPCs
This argument is an method, which takes an int and a bool, and returns a List of ints (List<int>)

As mentioned above, the given int is the NPC.whoAmI of the NPC who is having a boss bar drawn. The second input, the bool, will be set to true when the boss’s shield (if any) is active.

Your method is expected to return a list of the NPC.whoAmIs associated with any NPCs that contribute the boss’s cumulative life or shield value (Including the boss itself).
If you know how to make NPCs that function as parts of a boss, then going about this should be easy, seeing as you almost certainly have to do something along the lines of this in your NPCs’ code.

Make sure to only add vulnerable NPCs to this list! If not, the bar chip effect won’t function properly. If an NPC that is part of your boss has invulnerable states, exclude it from this list whenever it is invulnerable.

This list is used by Block’s Boss Bars to implement its bar shake and bar chip effects.


3: GetHP & 4: GetMaxHP
These arguments are methods, which take an int, and return a float

Your method simply needs to return the current and max life of the boss, respectively.


5: GetShield & 6: GetMaxShield
These arguments are methods, which take an int, and return a float

If your boss doesn't use a shield bar, then just make these return 0f, which indicates the shield is down (i.e. at 0%) and shouldn't be drawn.

If your boss does use a shield bar, your function should return the current and max values of the shield, respectively. This should be about as straightforward as HP, depending on what logic your boss uses for determining its shield status.


7: GetIcon
This argument is an method, which takes an int, and returns a Texture2D

The Texture2D you return should be of the boss's head/icon. Assuming you have set it normally in your boss's NPC class, you can retrieve it easily with the following code;
int bossHeadTextureIndex = Main.npc[npcWhoAmI].GetBossHeadTextureIndex(); return TextureAssets.NpcHeadBoss[bossHeadTextureIndex].Value;
Where npcWhoAmI is the given int.


8: GetString
This argument is an method, which takes an int, and returns a string

This is another straightforward return, simply return the boss’s displayed name.
For example, if you’re not doing anything special, the following code will suffice:
return Main.npc[npcWhoAmI].FullName;
Block’s Boss Bar automatically accounts for shields (by adding “ Shield” to the end of the name), so don’t worry about them if your boss uses the shield bar.

9 (OPTIONAL): isMiniboss
Unlike the past 6 arguments, this one is not a method, and is instead just a bool.

If true is passed in, then your custom boss bar logic will have a miniboss bar associated with it instead of a boss bar. This merely affects the visual style of the boss bar that draws. Ideal for making custom bar logic for minibosses.
As noted above, this argument is optional and may be left out if desired. Excluding this argument has the same effect as passing in false; the bar will be considered a fully fledged boss bar.




For more details on the Call and its arguments, feel free to inquiry here. It may also be beneficial to extract Block’s Boss Bars’ source (via. tML’s in-game extract function) and explore that. If you have the Corruption Core Boss mod, you can also extract that and check out its use of Mod.Call for an example.
Last edited by BlockCrusader; 2 Nov, 2024 @ 6:38pm