tModLoader Tutorial: [3] Items

Jofairden

Duke Fishron
tModLoader
Items
Last update: 9th of June, 2016
kdcROYP.png


Table of contents:

1. Prerequisites
2. Introduction
3. The first item
4. How to create any vanilla weapon type you want
5. Doing something on hit
6. Other things

kdcROYP.png

Prerequisites
Make sure you have....
  • ...the latest tModLoader installed (offical thread)
  • ...the latest Microsoft .NET Framework installed (offical .net site)
  • ...the Microsoft XNA Framework installed (you have this if you are able to play Terraria)
  • ...Microsoft Visual Studio (community = free) installed with the C# workspace (official MVS site)
  • .. actually, MVS isn't required but it's a very nice IDE to work with. You can also use notepad or notepadd++ or alike, but MVS will be super useful for noobs that makes simple mistakes because the IDE will help you program
  • ...C# knowledge, all tML mods currently are programmed with the C# language
  • ...followed the tutorial prior to this one http://forums.terraria.org/index.php?threads/tutorial-2-recipes.44822/
kdcROYP.png


Introduction
In this tutorial we're going to look at items in general. After recipes, items are generally the easiest to proceed with. Although, you can create very complicated items.In this tutorial, I will try to cover every item type for a custom item. (swords,spears,boomerang etc.) Complicated AI is for a later tutorial.

Before we begin, the SkeletonGenerator should already have created MyFirstItem.cs along with a sprite in your 'Items' folder.

kdcROYP.png


The first item
Let's take a look at MyFirstItem.cs It currently contains SetDefaults() and AddRecipes(), let's take a look.

SetDefaults()

Code:
        public override void SetDefaults()
        {
            item.name = "MyFirstItem";
            item.damage = 50;
            item.melee = true;
            item.width = 40;
            item.height = 40;
            item.toolTip = "This is a modded sword.";
            item.useTime = 20;
            item.useAnimation = 20;
            item.useStyle = 1;
            item.knockBack = 6;
            item.value = 10000;
            item.rare = 2;
            item.useSound = 1;
            item.autoReuse = true;
        }
This method (or hook) serves to set any properties of an item.
Most of these, should speak for themselves.
There are 5 damage types: item.melee, item.magic, item.ranged, item.summon and item.thrown
Each of these are booleans, you must set which damage type you want to use to true.
The item.width and item.height should generally be the size of the used sprite. These are the dimensions used in game. (hitbox etc.)

item.useTime determines how fast the item can actually be used. item.useAnimation actually determines how long it takes to perform the item's animation (in this case a swing)
You can not use the item again until the animation finishes, so you can have a long animation even though the item itself is very fast.

item.useStyle detemines which type of 'useStyle' is used, in this case 1 is an overhead swing. Here's a list of useStyles with examples:
  1. Swinging / Throwing (swords)
  2. Eating / Using (potions)
  3. Stabbing (shortswords)
  4. Holding up (summon items)
  5. Holdout out (spellbooks)
item.rare determines the rarity and color of the item. Here's a list of rarities you can use, along with their colors.
item.useSound determines which sound is used when using this item. In this case, 1 is general using sound. Here's a list of item useSounds:
  1. General Using Sound (for melee and most thrown stuff)
  2. Mushroom
  3. Potion Use
  4. Fallen Star, Life Crystal
  5. Arrow, Blowpipe Shooting Sound
  6. Magic Mirror
  7. Lower version of general using sound (deep swish)
  8. Demon Scythe, Dirt Rod, Orb of Light, Vilethorn
  9. Crystal Storm, Magic Missile, Star Cannon, Starfury
  10. Harpoon
  11. Guns
  12. Laser Rifle, Space Gun
  13. Water Spray
  14. Bomb Explosion
  15. Phaseblades
  16. Whoopie Cushion Fart
  17. Stinger Dart?
  18. Duplicate of #1
  19. Throwing sound (higher-pitched general use sound)
  20. Cursed Flames, Flamelash, Flower of Fire
  21. Water Bolt
  22. Motorized Tools (Drill, Chainsaw, Hamdrax loop this sound while being used)
  23. Motorized Tools Activation (plays with #22 at the start, but does not loop with it)
  24. Spectre Boots sound
  25. Fairy Bell
  26. Harp
  27. Coin Clink (Crystal Shard sound when broken)
  28. Ice Rod, Rainbow Rod
  29. Mana Crystal
  30. Ice Rod's Ice Block appearance sound
  31. Clockwork Assault Rifle
  32. Angel Wings / Demon Wings flapping sound
  33. Death Laser firing sound (Red lasers from the Destroyer and second-form Retinazer)
  34. Flamethrower
  35. Bell
  36. Shotgun
  37. Anvil clink
item.autoReuse determines whether the item can be reused by holding left click.

AddRecipes()
Hey, this is familiar! As said in the previous tutorial, there are various places to add recipes.
Let's take a look!
Code:
        public override void AddRecipes()
        {
            ModRecipe recipe = new ModRecipe(mod);
            recipe.AddIngredient(ItemID.DirtBlock, 10);
            recipe.AddTile(TileID.WorkBenches);
            recipe.SetResult(this);
            recipe.AddRecipe();
        }
As you can see, we are no longer passing "this" to our new ModRecipe as "this" would now refer to our ModItem, not our mod. That's why a mod variable has been opened up for you to use.
Instead, we can use "this" when setting our result, as we want our result to be our ModItem! The same recipe principles apply here, so there's nothing fancy to find.
kdcROYP.png


How to create any vanilla weapon type you want
There is a neat function we can make use of, called CloneDefaults()
The following new ModItem class could be pasted below your previous ModItem class, in the same file.
Code:
    public class BetterTerraBlade : ModItem
    {
        public override void SetDefaults()
        {
            item.CloneDefaults(ItemID.TerraBlade);
            item.name = "Better Terra Blade";
            item.damage = 500;
        }

        public override bool Autoload(ref string name, ref string texture, IList<EquipType> equips)
        {
            texture = "Terraria/Item_757";
            return true;
        }

        public override void AddRecipes()
        {
            ModRecipe recipe = new ModRecipe(mod);
            recipe.SetResult(this);
            recipe.AddRecipe();
        }
    }
This item will function exactly the same as a regular Terra Blade, but with 500 damage and a different name & texture.
I don't think I need to explain SetDefaults()


Overriding Autoload()
You don't have to override Autoload, the reason I'm doing it here is because I don't want to add a new sprite for this item: I want to use the vanilla Terra Blade sprite. We're manually setting the texure location. Remember if you want to access a mod's source, it starts from 'Mod Sources' so you need to begin with the mod's folder name. Autoload would normally look for a sprite named BetterTerraBlade.png which isn't there so we would get errors. You can access vanilla sprites by using "Terraria/" followed by the sprite name. Item sprites are named "Item_ID" where the ID is the ID of the item. For Terra Blade, the ID is 757. You can use Terraria.ID to get any ID as well as follows:
Code:
texture = "Terraria/Item_" + ItemID.TerraBlade;

An empty recipe?
To those of you who didn't know: it's possible to not require anything in a recipe. This allows us to craft this item without needing any ingredients. The only thing you have to do is simply not add any ingredient!

Custom drawing?
The above principles can be applied for any vanilla weapon. In the next example, I'm creating a Better Flairon ModItem. What's important to note here is that flails use custom drawing. No matter what you set the texture to, you'll see a Flairon texture when you use this item. This is due to manual drawing, which we will look at in a later tutorial. It will still display the texture we set in the inventory and any other place really.
Code:
    public class BetterFlairon : ModItem
    {
        public override void SetDefaults()
        {
            item.CloneDefaults(ItemID.Flairon);
            item.name = "Better Flairon";
            item.damage = 500;
        }

        public override bool Autoload(ref string name, ref string texture, IList<EquipType> equips)
        {
            texture = "Terraria/Item_" + ItemID.Flairon;
            return true;
        }

        public override void AddRecipes()
        {
            ModRecipe recipe = new ModRecipe(mod);
            recipe.SetResult(this);
            recipe.AddRecipe();
        }
    }
The trick with flails, same for certain other weapon types, is that they are throwing a projectile and the drawing happens in their AI. Again, this is something we should look at later.

A custom health potion
We can again use this to create a health potion that instantly heals us to full life! It's actually every easy!
Code:
    public class InstantHealPotion : ModItem
    {
        public override void SetDefaults()
        {
            item.CloneDefaults(ItemID.SuperHealingPotion);
            item.name = "Instant health potion";
            item.healLife = Main.player[item.owner].statLifeMax2;
        }

        public override bool Autoload(ref string name, ref string texture, IList<EquipType> equips)
        {
            texture = "Terraria/Item_" + ItemID.SuperHealingPotion;
            return true;
        }

        public override void AddRecipes()
        {
            ModRecipe recipe = new ModRecipe(mod);
            recipe.SetResult(this);
            recipe.AddRecipe();
        }
    }
The item is consumed upon use, but we are healed the following every time it's used:
Code:
item.healLife = Main.player[item.owner].statLifeMax2;
statLifeMax2 is the player's health INCLUDING buffs. statLifeMax is excluding buffs.
kdcROYP.png


Doing something onhit
I'm sure you know of those items that can set enemies ablaze. We can do exactly the same! Let's go back to our Better Terra Blade item, we can use the following hook to add a debuff when it hits something:
Code:
        public override void OnHitNPC(Player player, NPC target, int damage, float knockBack, bool crit)
        {
            target.AddBuff(BuffID.OnFire, 5 * 60);
        }
It's very important to note here that only the actual sword swung will apply this debuff, as we've not added this hook to the projectile. This is demonstrated in the following picture
eeaaa6cf06774e6fb3cc9d586287ef31.png

The first dummy was hit by our actual sword, the second one was only hit by the projectile. As projectiles do not cover this tutorial, unfortunately I will not go into this now.

Something more unique
Adding debuffs on hit isn't just the only thing you can do. You could for example deal some damage to the player when hitting an npc that is a town npc!
Code:
        public override void OnHitNPC(Player player, NPC target, int damage, float knockBack, bool crit)
        {
            target.AddBuff(BuffID.OnFire, 5 * 60);

            if (target.townNPC)
            {
                player.Hurt(5, -player.direction, false, false, " is an evil :red:...");
            }
        }
The above code would damage the player by 5 with a knockback to the opposite direction. If you die, it uses the custom text "Player is an evil :red:..."

kdcROYP.png


Other things
I will fill the following list as time progresses. If you want me to cover something here, let me now in a comment.

Custom CanUseItem rules
We can start using the CanUseItem() hook to decide whether or not an item can be used.
Let's go back to our Better Flairon item add the following: the item can only be used if the player is in hardmode.
Code:
        public override bool CanUseItem(Player player)
        {
            return Main.hardMode;
        }

If you return true in this hook, the item can be used. Vice versa for false. Try it out! Use the next example if you want to test this more easily.

UseItem rules

No hardmode? Let's make it so that our potion toggles the hardMode variable for testing purposes.
Add the following in InstantHealPotion:
Code:
        public override bool UseItem(Player player)
        {
            Main.hardMode = !Main.hardMode;
            return base.UseItem(player);
        }
We are now using the UseItem() hook to do stuff when the item is used. The above code will reverse Main.hardMode.
If your world isn't hardMode, consume this potion and you will be able to use Better Flairon! Consume another potion and you will no longer be able to!
It's magic! ;)


WIP, MORE TO COME



kdcROYP.png

Full code
Code:
using System.Collections.Generic;
using Terraria;
using Terraria.ID;
using Terraria.ModLoader;

namespace MyFirstMod.Items
{
    public class MyFirstItem : ModItem
    {
        public override void SetDefaults()
        {
            item.name = "MyFirstItem";
            item.damage = 50;
            item.width = 40;
            item.height = 40;
            item.toolTip = "This is a modded sword.";
            item.useTime = 20;
            item.useAnimation = 20;
            item.useStyle = 1;
            item.knockBack = 6;
            item.value = 10000;
            item.rare = 2;
            item.useSound = 1;
            item.autoReuse = true;
        }

        public override void AddRecipes()
        {
            ModRecipe recipe = new ModRecipe(mod);
            recipe.AddIngredient(ItemID.DirtBlock, 10);
            recipe.AddTile(TileID.WorkBenches);
            recipe.SetResult(this);
            recipe.AddRecipe();
        }
    }

    public class BetterTerraBlade : ModItem
    {
        public override void SetDefaults()
        {
            item.CloneDefaults(ItemID.TerraBlade);
            item.name = "Better Terra Blade";
            item.damage = 500;
        }

        public override void OnHitNPC(Player player, NPC target, int damage, float knockBack, bool crit)
        {
            target.AddBuff(BuffID.OnFire, 5 * 60);

            if (target.townNPC)
            {
                player.Hurt(5, -player.direction, false, false, " is an evil :red:...");
            }
        }

        public override bool Autoload(ref string name, ref string texture, IList<EquipType> equips)
        {
            texture = "Terraria/Item_" + ItemID.TerraBlade;
            return true;
        }

        public override void AddRecipes()
        {
            ModRecipe recipe = new ModRecipe(mod);
            recipe.SetResult(this);
            recipe.AddRecipe();
        }
    }

    public class BetterFlairon : ModItem
    {
        public override void SetDefaults()
        {
            item.CloneDefaults(ItemID.Flairon);
            item.name = "Better Flairon";
            item.damage = 500;
        }

        public override bool Autoload(ref string name, ref string texture, IList<EquipType> equips)
        {
            texture = "Terraria/Item_" + ItemID.Flairon;
            return true;
        }

        public override bool CanUseItem(Player player)
        {
            return Main.hardMode;
        }

        public override void AddRecipes()
        {
            ModRecipe recipe = new ModRecipe(mod);
            recipe.SetResult(this);
            recipe.AddRecipe();
        }
    }

    public class InstantHealPotion : ModItem
    {
        public override void SetDefaults()
        {
            item.CloneDefaults(ItemID.SuperHealingPotion);
            item.name = "Instant health potion";
            item.healLife = Main.player[item.owner].statLifeMax2;
        }

        public override bool UseItem(Player player)
        {
            Main.hardMode = !Main.hardMode;
            return base.UseItem(player);
        }

        public override bool Autoload(ref string name, ref string texture, IList<EquipType> equips)
        {
            texture = "Terraria/Item_" + ItemID.SuperHealingPotion;
            return true;
        }

        public override void AddRecipes()
        {
            ModRecipe recipe = new ModRecipe(mod);
            recipe.SetResult(this);
            recipe.AddRecipe();
        }
    }
}



kdcROYP.png


Go to next tutorial: Tutorial [3] Projectiles
 
Last edited:

neoselket

Ice Queen
when i put an item.cs file and an item.png file in my items folder, it loads the mod fine but the item doesn't show up. not only can i not craft it, but the item doesn't even exist(i tested it with cheat sheet). added crafting recipes for vanilla items work fine, but the modded items don't. the same files(item.cs and item.png) work fine in another mod folder, but not this one. here's my(mod name is plasma) plasma.cs file:

using System;
using Microsoft.Xna.Framework;
using Terraria;
using Terraria.ID;
using Terraria.ModLoader;

namespace plasma {
public class plasma : Mod
{
public override void AddRecipes()
{
RecipeHelper.AddEndurancePotionRecipes(this);
}
}
}
 

Jofairden

Duke Fishron
tModLoader
when i put an item.cs file and an item.png file in my items folder, it loads the mod fine but the item doesn't show up. not only can i not craft it, but the item doesn't even exist(i tested it with cheat sheet). added crafting recipes for vanilla items work fine, but the modded items don't. the same files(item.cs and item.png) work fine in another mod folder, but not this one. here's my(mod name is plasma) plasma.cs file:

using System;
using Microsoft.Xna.Framework;
using Terraria;
using Terraria.ID;
using Terraria.ModLoader;

namespace plasma {
public class plasma : Mod
{
public override void AddRecipes()
{
RecipeHelper.AddEndurancePotionRecipes(this);
}
}
}
You're not autoloading, so the item isn't being 'registrered'. Add the following:
Code:
        public plasma()
        {
            Properties = new ModProperties()
            {
                Autoload = true,
                AutoloadGores = true,
                AutoloadSounds = true
            };
        }
 

neoselket

Ice Queen
ok, it looks like this now, but i get an error when i try to build it. i'm assuming i shouldn't have put it at the end, but i'm not sure where i should have put it:

thanks for your help!:)

using System;
using Microsoft.Xna.Framework;
using Terraria;
using Terraria.ID;
using Terraria.ModLoader;

namespace plasma {
public class plasma : Mod
{
public override void AddRecipes()
{
RecipeHelper.AddEndurancePotionRecipes(this);
}
}
}
public plasma()
{
Properties = new ModProperties()
{
Autoload = true,
AutoloadGores = true,
AutoloadSounds = true
};
}
 
Last edited:

Eli10293

Spazmatism
Items
Last update: 9th of June, 2016
kdcROYP.png


Table of contents:

1. Prerequisites
2. Introduction
3. The first item
4. How to create any vanilla weapon type you want
5. Doing something on hit
6. Other things

kdcROYP.png

Prerequisites
Make sure you have....
  • ...the latest tModLoader installed (offical thread)
  • ...the latest Microsoft .NET Framework installed (offical .net site)
  • ...the Microsoft XNA Framework installed (you have this if you are able to play Terraria)
  • ...Microsoft Visual Studio (community = free) installed with the C# workspace (official MVS site)
  • .. actually, MVS isn't required but it's a very nice IDE to work with. You can also use notepad or notepadd++ or alike, but MVS will be super useful for noobs that makes simple mistakes because the IDE will help you program
  • ...C# knowledge, all tML mods currently are programmed with the C# language
  • ...followed the tutorial prior to this one http://forums.terraria.org/index.php?threads/tutorial-2-recipes.44822/
kdcROYP.png


Introduction
In this tutorial we're going to look at items in general. After recipes, items are generally the easiest to proceed with. Although, you can create very complicated items.In this tutorial, I will try to cover every item type for a custom item. (swords,spears,boomerang etc.) Complicated AI is for a later tutorial.

Before we begin, the SkeletonGenerator should already have created MyFirstItem.cs along with a sprite in your 'Items' folder.
kdcROYP.png


The first item
Let's take a look at MyFirstItem.cs It currently contains SetDefaults() and AddRecipes(), let's take a look.

SetDefaults()

Code:
        public override void SetDefaults()
        {
            item.name = "MyFirstItem";
            item.damage = 50;
            item.melee = true;
            item.width = 40;
            item.height = 40;
            item.toolTip = "This is a modded sword.";
            item.useTime = 20;
            item.useAnimation = 20;
            item.useStyle = 1;
            item.knockBack = 6;
            item.value = 10000;
            item.rare = 2;
            item.useSound = 1;
            item.autoReuse = true;
        }
This method (or hook) serves to set any properties of an item.
Most of these, should speak for themselves.
There are 5 damage types: item.melee, item.magic, item.ranged, item.summon and item.thrown
Each of these are booleans, you must set which damage type you want to use to true.
The item.width and item.height should generally be the size of the used sprite. These are the dimensions used in game. (hitbox etc.)

item.useTime determines how fast the item can actually be used. item.useAnimation actually determines how long it takes to perform the item's animation (in this case a swing)
You can not use the item again until the animation finishes, so you can have a long animation even though the item itself is very fast.

item.useStyle detemines which type of 'useStyle' is used, in this case 1 is an overhead swing. Here's a list of useStyles with examples:
  1. Swinging / Throwing (swords)
  2. Eating / Using (potions)
  3. Stabbing (shortswords)
  4. Holding up (summon items)
  5. Holdout out (spellbooks)
item.rare determines the rarity and color of the item. Here's a list of rarities you can use, along with their colors.
item.useSound determines which sound is used when using this item. In this case, 1 is general using sound. Here's a list of item useSounds:
  1. General Using Sound (for melee and most thrown stuff)
  2. Mushroom
  3. Potion Use
  4. Fallen Star, Life Crystal
  5. Arrow, Blowpipe Shooting Sound
  6. Magic Mirror
  7. Lower version of general using sound (deep swish)
  8. Demon Scythe, Dirt Rod, Orb of Light, Vilethorn
  9. Crystal Storm, Magic Missile, Star Cannon, Starfury
  10. Harpoon
  11. Guns
  12. Laser Rifle, Space Gun
  13. Water Spray
  14. Bomb Explosion
  15. Phaseblades
  16. Whoopie Cushion Fart
  17. Stinger Dart?
  18. Duplicate of #1
  19. Throwing sound (higher-pitched general use sound)
  20. Cursed Flames, Flamelash, Flower of Fire
  21. Water Bolt
  22. Motorized Tools (Drill, Chainsaw, Hamdrax loop this sound while being used)
  23. Motorized Tools Activation (plays with #22 at the start, but does not loop with it)
  24. Spectre Boots sound
  25. Fairy Bell
  26. Harp
  27. Coin Clink (Crystal Shard sound when broken)
  28. Ice Rod, Rainbow Rod
  29. Mana Crystal
  30. Ice Rod's Ice Block appearance sound
  31. Clockwork Assault Rifle
  32. Angel Wings / Demon Wings flapping sound
  33. Death Laser firing sound (Red lasers from the Destroyer and second-form Retinazer)
  34. Flamethrower
  35. Bell
  36. Shotgun
  37. Anvil clink
item.autoReuse determines whether the item can be reused by holding left click.

AddRecipes()
Hey, this is familiar! As said in the previous tutorial, there are various places to add recipes.
Let's take a look!
Code:
        public override void AddRecipes()
        {
            ModRecipe recipe = new ModRecipe(mod);
            recipe.AddIngredient(ItemID.DirtBlock, 10);
            recipe.AddTile(TileID.WorkBenches);
            recipe.SetResult(this);
            recipe.AddRecipe();
        }
As you can see, we are no longer passing "this" to our new ModRecipe as "this" would now refer to our ModItem, not our mod. That's why a mod variable has been opened up for you to use.
Instead, we can use "this" when setting our result, as we want our result to be our ModItem! The same recipe principles apply here, so there's nothing fancy to find.
kdcROYP.png


How to create any vanilla weapon type you want
There is a neat function we can make use of, called CloneDefaults()
The following new ModItem class could be pasted below your previous ModItem class, in the same file.
Code:
    public class BetterTerraBlade : ModItem
    {
        public override void SetDefaults()
        {
            item.CloneDefaults(ItemID.TerraBlade);
            item.name = "Better Terra Blade";
            item.damage = 500;
        }

        public override bool Autoload(ref string name, ref string texture, IList<EquipType> equips)
        {
            texture = mod.Name + "/Items/MyFirstItem";
            return true;
        }

        public override void AddRecipes()
        {
            ModRecipe recipe = new ModRecipe(mod);
            recipe.SetResult(this);
            recipe.AddRecipe();
        }
    }
This item will function exactly the same as a regular Terra Blade, but with 500 damage and a different name & texture.
I don't think I need to explain SetDefaults()


Overriding Autoload()
You don't have to override Autoload, the reason I'm doing it here is because I don't want to add a new sprite for this item: it can use the existing MyFirstItem.png sprite. We're manually setting the texure location. Remember it starts from 'Mod Sources' so you need to begin with your mod's folder name. Autoload would normally look for a sprite named BetterTerraBlade.png which isn't there so we would get errors.

An empty recipe?
To those of you who didn't know: it's possible to not require anything in a recipe. This allows us to craft this item without needing any ingredients. The only thing you have to do is simply not add any ingredient!

Custom drawing?
The above principles can be applied for any vanilla weapon. In the next example, I'm creating a Better Flairon ModItem. What's important to note here is that we'll no longer see our sword swing when using this item, instead we see the actual Flairon, even though we've set to use our MyFirstItem.png texture in Autoload(). This is due to manual drawing, which we will look at in a later tutorial. It will still display the MyFirstItem.png texture in your inventory, or anywhere else really.
Code:
    public class BetterFlairon : ModItem
    {
        public override void SetDefaults()
        {
            item.CloneDefaults(ItemID.Flairon);
            item.name = "Better Flairon";
            item.damage = 500;
        }

        public override bool Autoload(ref string name, ref string texture, IList<EquipType> equips)
        {
            texture = mod.Name + "/Items/MyFirstItem";
            return true;
        }

        public override void AddRecipes()
        {
            ModRecipe recipe = new ModRecipe(mod);
            recipe.SetResult(this);
            recipe.AddRecipe();
        }
    }
The trick with flails, same for certain other weapon types, is that they are throwing a projectile and the drawing happens in their AI. Again, this is something we should look at later.

A custom health potion
We can again use this to create a health potion that instantly heals us to full life! It's actually every easy!
Code:
    public class InstantHealPotion : ModItem
    {
        public override void SetDefaults()
        {
            item.CloneDefaults(ItemID.SuperHealingPotion);
            item.name = "Instant health potion";
            item.healLife = Main.player[item.owner].statLifeMax2;
        }

        public override bool Autoload(ref string name, ref string texture, IList<EquipType> equips)
        {
            texture = mod.Name + "/Items/MyFirstItem";
            return true;
        }

        public override void AddRecipes()
        {
            ModRecipe recipe = new ModRecipe(mod);
            recipe.SetResult(this);
            recipe.AddRecipe();
        }
    }
The item is consumed upon use, but we are healed the following every time it's used:
Code:
item.healLife = Main.player[item.owner].statLifeMax2;
statLifeMax2 is the player's health INCLUDING buffs. statLifeMax is excluding buffs.
Also, this item again would use our MyFirstItem.png sprite, which obviously looks quite ugly for a potion. (this is done so we don't need to continously add new sprites)
kdcROYP.png


Doing something onhit
I'm sure you know of those items that can set enemies ablaze. We can do exactly the same! Let's go back to our Better Terra Blade item, we can use the following hook to add a debuff when it hits something:
Code:
        public override void OnHitNPC(Player player, NPC target, int damage, float knockBack, bool crit)
        {
            target.AddBuff(BuffID.OnFire, 5 * 60);
        }
It's very important to note here that only the actual sword swung will apply this debuff, as we've not added this hook to the projectile. This is demonstrated in the following picture
eeaaa6cf06774e6fb3cc9d586287ef31.png

The first dummy was hit by our actual sword, the second one was only hit by the projectile. As projectiles do not cover this tutorial, unfortunately I will not go into this now.

Something more unique
Adding debuffs on hit isn't just the only thing you can do. You could for example deal some damage to the player when hitting an npc that is a town npc!
Code:
        public override void OnHitNPC(Player player, NPC target, int damage, float knockBack, bool crit)
        {
            target.AddBuff(BuffID.OnFire, 5 * 60);

            if (target.townNPC)
            {
                player.Hurt(5, -player.direction, false, false, " is an evil :red:...");
            }
        }
The above code would damage the player by 5 with a knockback to the opposite direction. If you die, it uses the custom text "Player is an evil :red:..."

kdcROYP.png


Other things
I will fill the following list as time progresses. If you want me to cover something here, let me now in a comment.

Custom CanUseItem rules
We can start using the CanUseItem() hook to decide whether or not an item can be used.
Let's go back to our Better Flairon item add the following: the item can only be used if the player is in hardmode.
Code:
        public override bool CanUseItem(Player player)
        {
            return Main.hardMode;
        }

If you return true in this hook, the item can be used. Vice versa for false. Try it out! Use the next example if you want to test this more easily.

UseItem rules

No hardmode? Let's make it so that our potion toggles the hardMode variable for testing purposes.
Add the following in InstantHealPotion:
Code:
        public override bool UseItem(Player player)
        {
            Main.hardMode = !Main.hardMode;
            return base.UseItem(player);
        }
We are now using the UseItem() hook to do stuff when the item is used. The above code will reverse Main.hardMode.
If your world isn't hardMode, consume this potion and you will be able to use Better Flairon! Consume another potion and you will no longer be able to!
It's magic! ;)


WIP, MORE TO COME



kdcROYP.png



Go to next tutorial: not yet available
I remember back in tapi when there was a way to change the AI style of a projectile fired just from within the cs file of my custom weapon
Is it possible to tModLoader?
 

Jofairden

Duke Fishron
tModLoader
I remember back in tapi when there was a way to change the AI style of a projectile fired just from within the cs file of my custom weapon
Is it possible to tModLoader?
You can not change the AI style of a projectile from within ModItem.
ok, it looks like this now, but i get an error when i try to build it. i'm assuming i shouldn't have put it at the end, but i'm not sure where i should have put it:

thanks for your help!:)

snip
You messed up several closing and opening curly brackets ({ and }). Are you using an IDE such as Visual Studio? They will make sure these things don't happen.
Here's the correct code. Also next time, please open logs and copy & paste the error, it helps a lot.
Code:
using System;
using Microsoft.Xna.Framework;
using Terraria;
using Terraria.ID;
using Terraria.ModLoader;

namespace plasma
{
    public class plasma : Mod
    {
        public override void AddRecipes()
        {
        RecipeHelper.AddEndurancePotionRecipes(this);
        }
       
        public plasma()
        {
            Properties = new ModProperties()
            {
                Autoload = true,
                AutoloadGores = true,
                AutoloadSounds = true
            };
        }
}
 

Eli10293

Spazmatism
You can not change the AI style of a projectile from within ModItem.

You messed up several closing and opening curly brackets ({ and }). Are you using an IDE such as Visual Studio? They will make sure these things don't happen.
Here's the correct code. Also next time, please open logs and copy & paste the error, it helps a lot.
Code:
using System;
using Microsoft.Xna.Framework;
using Terraria;
using Terraria.ID;
using Terraria.ModLoader;

namespace plasma
{
    public class plasma : Mod
    {
        public override void AddRecipes()
        {
        RecipeHelper.AddEndurancePotionRecipes(this);
        }
     
        public plasma()
        {
            Properties = new ModProperties()
            {
                Autoload = true,
                AutoloadGores = true,
                AutoloadSounds = true
            };
        }
}
Would there be a way to accomplish this outside of it?
There was a way in tAPI but I had decompiled the tapi version of avalon to find it nad it was inside the item's .cs file
 

Jofairden

Duke Fishron
tModLoader
Would there be a way to accomplish this outside of it?
There was a way in tAPI but I had decompiled the tapi version of avalon to find it nad it was inside the item's .cs file
You can set the projectile's properties inside the ModProjectile class, using SetDefaults()
Next tutorial covers projectiles.
 

Eli10293

Spazmatism
You can set the projectile's properties inside the ModProjectile class, using SetDefaults()
Next tutorial covers projectiles.
I was referring to this item from avalon
Code:
using System;
using System.Collections.Generic;
using System.Linq;
using Microsoft.Xna.Framework;
using Terraria;
using TAPI;

namespace Avalon.Items.Weapons.Ranged.Bows
{
    /// <summary>
    /// The Verbrae Bow.
    /// </summary>
    public class VertebraeBow : ModItem
    {
        /// <summary>
        ///
        /// </summary>
        /// <param name="p"></param>
        /// <param name="pos"></param>
        /// <param name="vel"></param>
        /// <param name="type"></param>
        /// <param name="dmg"></param>
        /// <param name="kb"></param>
        /// <returns></returns>
        public override bool PreShoot(Player p, Vector2 pos, Vector2 vel, int type, int dmg, float kb)
        {
            Projectile arr = Main.projectile[Projectile.NewProjectile(p.Centre.X, p.Centre.Y,vel.X, vel.Y, 278, dmg, kb, p.whoAmI)];
            arr.aiStyle = 8; // 207 Chloro Bullets 297 Spectre Staff
            arr.penetrate = 2;

            return false;
        }
    }
}
 

Jofairden

Duke Fishron
tModLoader
I was referring to this item from avalon
Code:
using System;
using System.Collections.Generic;
using System.Linq;
using Microsoft.Xna.Framework;
using Terraria;
using TAPI;

namespace Avalon.Items.Weapons.Ranged.Bows
{
    /// <summary>
    /// The Verbrae Bow.
    /// </summary>
    public class VertebraeBow : ModItem
    {
        /// <summary>
        ///
        /// </summary>
        /// <param name="p"></param>
        /// <param name="pos"></param>
        /// <param name="vel"></param>
        /// <param name="type"></param>
        /// <param name="dmg"></param>
        /// <param name="kb"></param>
        /// <returns></returns>
        public override bool PreShoot(Player p, Vector2 pos, Vector2 vel, int type, int dmg, float kb)
        {
            Projectile arr = Main.projectile[Projectile.NewProjectile(p.Centre.X, p.Centre.Y,vel.X, vel.Y, 278, dmg, kb, p.whoAmI)];
            arr.aiStyle = 8; // 207 Chloro Bullets 297 Spectre Staff
            arr.penetrate = 2;

            return false;
        }
    }
}
Ooh did you mean like that. Yes that's possible, but only after the actual projectile is spawned. I thought you meant changing it directly. What this does, is it spawns a projectile, then changes that projectile's aiStyle to 8. But only that one spawned projectile. If you spawn another one, it will not have aiStyle 8.
 

Eli10293

Spazmatism
Ooh did you mean like that. Yes that's possible, but only after the actual projectile is spawned. I thought you meant changing it directly. What this does, is it spawns a projectile, then changes that projectile's aiStyle to 8. But only that one spawned projectile. If you spawn another one, it will not have aiStyle 8.
That was what I meant :)
Is it possible to make this code work with tmodloader?
 

Jofairden

Duke Fishron
tModLoader
That was what I meant :)
Is it possible to make this code work with tmodloader?
Yes, it'll work, so long as you know the index of the spawned projectile.

Also little update, I didn't know you could actually Autoload vanilla textures. I've updated OP to refelect this. Basically it is as follows in Autoload()
Code:
texture = "Terraria/Item_" + ItemID.Flairon;
You can change Flairon to whatever vanilla item's texture you want to use.
 

NightX

Terrarian
Well, i'm trying to make a mod just for fun but i dont know any good ways to do this without altering tModLoader itself.

I want to make a mod that alters all vanilla weapons with this condition
  • I can use a certain custom item on recipe to "upgrade" this item, having a little boost on attack.
  • that item would be permanent, and i can upgrade it to for more damage
  • any weapon can be upgrade infinitelly.
Is there a way to do this without making one by one?
 

Barney Bagon

Terrarian
Someone help im getting this error when i try to put my pickaxe in:

c:\Users\Home\Documents\My Games\Terraria\ModLoader\Mod Sources\TheDeltaMod\TheDeltaMod.cs(7,7) : warning CS0105: The using directive for 'Terraria.ModLoader' appeared previously in this namespace

c:\Users\Home\Documents\My Games\Terraria\ModLoader\Mod Sources\TheDeltaMod\Items\Pickaxes\DeltaPickaxe.cs(27,17) : error CS0201: Only assignment, call, increment, decrement, await, and new object expressions can be used as a statement

c:\Users\Home\Documents\My Games\Terraria\ModLoader\Mod Sources\TheDeltaMod\Items\Pickaxes\DeltaPickaxe.cs(27,17) : error CS0019: Operator '-' cannot be applied to operands of type 'bool' and 'bool'



This is my CODE

Code:
using Microsoft.Xna.Framework;
using Terraria;
using Terraria.ID;
using Terraria.ModLoader;

namespace TheDeltaMod.Items.Weapons
{
  public class DeltaPickaxe : ModItem
  {
  public override void SetDefaults()
  {
  item.name = "Delta Pickaxe";
  item.damage = 18;
  item.melee = true;
  item.width = 64;
  item.height = 64;
  item.toolTip = "The Delta Pickaxe";
  item.useTime = 15;
  item.useAnimation = 20;
  item.pick = 100;
  item.useStyle = 1;
  item.knockBack = 6;
  item.value = 10;
  item.rare = 2;
  item.useSound = 1;
  item.autoReuse = true;
  item.useTurn - true;
  }
  public override void AddRecipes()
  {
  ModRecipe recipe = new ModRecipe(mod);
  recipe.AddIngredient(ItemID.DirtBlock, 1);
  recipe.AddTile(TileID.Anvils);
  recipe.SetResult(this);
  recipe.AddRecipe();
  }
  }
}
 

Snrasha

Terrarian
Someone help im getting this error when i try to put my pickaxe in:

c:\Users\Home\Documents\My Games\Terraria\ModLoader\Mod Sources\TheDeltaMod\TheDeltaMod.cs(7,7) : warning CS0105: The using directive for 'Terraria.ModLoader' appeared previously in this namespace

c:\Users\Home\Documents\My Games\Terraria\ModLoader\Mod Sources\TheDeltaMod\Items\Pickaxes\DeltaPickaxe.cs(27,17) : error CS0201: Only assignment, call, increment, decrement, await, and new object expressions can be used as a statement

c:\Users\Home\Documents\My Games\Terraria\ModLoader\Mod Sources\TheDeltaMod\Items\Pickaxes\DeltaPickaxe.cs(27,17) : error CS0019: Operator '-' cannot be applied to operands of type 'bool' and 'bool'



This is my CODE

Code:
using Microsoft.Xna.Framework;
using Terraria;
using Terraria.ID;
using Terraria.ModLoader;

namespace TheDeltaMod.Items.Weapons
{
  public class DeltaPickaxe : ModItem
  {
  public override void SetDefaults()
  {
  item.name = "Delta Pickaxe";
  item.damage = 18;
  item.melee = true;
  item.width = 64;
  item.height = 64;
  item.toolTip = "The Delta Pickaxe";
  item.useTime = 15;
  item.useAnimation = 20;
  item.pick = 100;
  item.useStyle = 1;
  item.knockBack = 6;
  item.value = 10;
  item.rare = 2;
  item.useSound = 1;
  item.autoReuse = true;
  item.useTurn - true;
  }
  public override void AddRecipes()
  {
  ModRecipe recipe = new ModRecipe(mod);
  recipe.AddIngredient(ItemID.DirtBlock, 1);
  recipe.AddTile(TileID.Anvils);
  recipe.SetResult(this);
  recipe.AddRecipe();
  }
  }
}
namespace TheDeltaMod.Items.WeaponsPickaxes <<<<<<


item.useTurn = true; <<<<<<<<<<

Install VisualStudio, he say where you have a error.
 

Jofairden

Duke Fishron
tModLoader
Well, i'm trying to make a mod just for fun but i dont know any good ways to do this without altering tModLoader itself.

I want to make a mod that alters all vanilla weapons with this condition
  • I can use a certain custom item on recipe to "upgrade" this item, having a little boost on attack.
  • that item would be permanent, and i can upgrade it to for more damage
  • any weapon can be upgrade infinitelly.
Is there a way to do this without making one by one?
If you'd like to alter vanilla items like this, it might be worth looking into ItemInfo. ItemInfo allows you to 'add' and customize your own custom info about an item. Think of it like this: normally you have item.melee, which if true, the item deals melee damage. With ItemInfo, you could add custom damage for example. You could apply the same tactics into upgrading the item. For example, if a certain condition is met (most likely a bool in the ItemInfo is set to true), then the damage of the item increases.
 
Top Bottom