TAPI makes modding extremely easy and adds hooks for many things such as items and projectiles; however, one thing it doesn't seem to have an obvious hook for is dust (the particles that are made by things like torches, terra blade, etc). This can get extremely frustrating when one realizes that nearly everything about dust (shape, color, behavior, light color, etc.) is very hard-coded into the game. This tutorial will teach you how to add custom dust to the game and completely control its behavior. (Warning: everything will be done with .cs files, so you actually need to know how to program.)
First, you will need to create a class for your dust (actually, you don't need to, but it makes organization much, much easier). As an example, I will use the mod I am currently working on at the time of writing this. You will need to add several things: a field to keep track of the texture for your custom dust, and a method to assign the texture to the field.
Next, in your ModBase class, you will need to add the following to your OnLoad method in order for your dust class to actually be able to access the texture:
Now you have everything you need to start creating your custom dust. Now for actually creating custom dust, go back to the custom dust class. I feel that the easiest way to teach you will be to show an example:
You can look through the Terraria.Dust class for more examples of dust behavior (although admittedly it's hard to look through). Basically, using these two methods, you can completely control the behavior of your dust. Then to spawn the dust, just call the create method.
There is still one thing we're missing; the actual texture for your dust. Now to explain how to make a texture file for your dust. The dust must have a size of 8 x 8 pixels (it can be smaller, just make sure it stays within the 8 x 8 square). Now, whenever dust spawns, it is given one out of three textures at random. So draw your first image in the 8 x 8 square location at the coordinates (0, 0) of the image. Then, two pixels below this 8 x 8 square, draw the second image, also in an 8 x 8 square. For the third image, draw it in another 8 x 8 square two pixels below the second image. Here is the example from my mod:
I basically gave the three dusts different brightnesses; you might want to be more creative with your differences, depending on what you need.
Remember how in your code, you had to specify the type of dust? These are the textures that type 0 will use. If you want another type of dust with a different texture, give it a type of 1. Then 2 pixels to the right of the type 0 textures, repeat the same process. You can keep repeating this for more and more dusts. There is one catch: if you end up having more than 100 dust types, then place type 100 2 pixels below type 0, instead of further to the right. Then add the next dust textures to the right of that, repeat for the next 100 dusts. For example, you can see the Dust.png that the vanilla game uses. Finally, remember that the dust textures are completely contained within the 8 x 8 squares; when I say 2 pixels to the right or down, I mean an 8 x 8 square 2 pixels away from another 8 x 8 square.
Here is the end result of the dust in my mod:
Remember, to create the dust, just call your create method for the type of dust and provide the coordinates. Since the method returns the dust's index, you can customize it even more after you create it (i.e. if you want it to behave differently when produced from different sources). Feel free to ask any questions you have
First, you will need to create a class for your dust (actually, you don't need to, but it makes organization much, much easier). As an example, I will use the mod I am currently working on at the time of writing this. You will need to add several things: a field to keep track of the texture for your custom dust, and a method to assign the texture to the field.
Code:
using System;
using Microsoft.Xna.Framework; //This will help you control the behavior of the dust, which we'll go over later.
using Microsoft.Xna.Framework.Graphics; //This is where Texture2D is located.
using Terraria;
using TAPI;
namespace Bluemagic {
public class BluemagicDust
{
private static Texture2D texture; //This stores the custom dust textures for your class to use.
public static void Load(ModBase modBase) //You can name this anything you want; just make sure it takes TAPI.ModBase as a parameter.
{
texture = modBase.textures["Dust"]; //This gets a texture from Dust.png in your mod folder then assigns it to texture.
}
}}
Next, in your ModBase class, you will need to add the following to your OnLoad method in order for your dust class to actually be able to access the texture:
Code:
using System;
using Terraria;
using TAPI;
namespace Bluemagic {
public class Bluemagic : ModBase
{
public override void OnLoad()
{
BluemagicDust.Load(this); //Use whatever you named your method from the previous part.
//Your other loading stuff
}
//Your other methods
}}
Now you have everything you need to start creating your custom dust. Now for actually creating custom dust, go back to the custom dust class. I feel that the easiest way to teach you will be to show an example:
Code:
using System;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Graphics;
using Terraria;
using TAPI;
namespace Bluemagic {
public class BluemagicDust
{
private static Texture2D texture;
public static void Load(ModBase modBase)
{
texture = modBase.textures["Dust"];
}
public static int CreateSpectreDust(float x, float y, int width, int height) //This is the method your other classes will use in order to spawn this dust.
{
Color color = new Color(200, 220, 230); //This is the color multiplier of your dust; The dust image you create will get "multiplied" by this color. If you don't know what the numbers mean, go look up RGB values.
int dust = Dust.NewDust(new Vector2(x, y), width, height, 0, 0f, 0f, 100, color, 1.2f); //The parameters are (Microsoft.Xna.Framework.Vector2 position, int width, int height, int type, float xVelocity, float yVelocity, int alpha, Microsoft.Xna.Framework.Color color, float scale).
//The method returns the index of your dust, so to access the new dust, all you need to do is call Main.dust[whatever was returned].
//I'm hoping that position and the velocities are self-explanatory.
//The width and height are basically the range of positions in which the dust will randomly spawn. Useful if you want a dust to spawn at any random point within a projectile, or something like that.
//The type is basically the texture your dust will use. We will go over this later.
//Alpha is the transparency of your dust. 0 is fully opaque, and 255 is fully invisible.
//Color is the color multiplier on your dust.
//Scale is the size of your dust; the size of the image will get multiplied by the scale.
Main.dust[dust].noGravity = true; //Self-explanatory.
Main.dust[dust].velocity /= 2; //This halves the speed of my dust when it spawns.
Main.dust[dust].OverrideTexture = texture; //This is necessary for your dust to use your custom texture.
Main.dust[dust].OverrideLightColor = color; //This makes the dust always appear a certain color, regardless of what kind of light is hitting it.
Main.dust[dust].OverrideUpdate = UpdateSpectreDust; //This is what controls the behavior of the dust. See next method for details.
return dust; //This is so whatever creates your dust can access it, similar to how Dust.NewDust returns the same thing.
}
private static void UpdateSpectreDust(Dust dust) //This is the method I use to control the behavior of my dust. Make sure it takes Terraria.Dust as the one and only parameter. This method will get called for every game tick.
{
dust.position += dust.velocity; //Necessary for the dust to actually move.
dust.rotation += dust.velocity.X; //Rotating your dust may make it look more realistic; it's up to you how you do so.
Lighting.AddLight((int)(dust.position.X / 16f), (int)(dust.position.Y / 16f), 0.05f, 0.15f, 0.2f); //The last three parameters are RGB values, except instead of integers from 0 to 255 it's real numbers from 0 to 1 (you could make it more than 1 although that would be really bright).
dust.scale -= 0.03f; //This makes the dust shrink as time passes.
if(dust.scale < 0.5f)
{
dust.active = false; //This removes the dust; you don't want dust to last forever.
}
}
}}
There is still one thing we're missing; the actual texture for your dust. Now to explain how to make a texture file for your dust. The dust must have a size of 8 x 8 pixels (it can be smaller, just make sure it stays within the 8 x 8 square). Now, whenever dust spawns, it is given one out of three textures at random. So draw your first image in the 8 x 8 square location at the coordinates (0, 0) of the image. Then, two pixels below this 8 x 8 square, draw the second image, also in an 8 x 8 square. For the third image, draw it in another 8 x 8 square two pixels below the second image. Here is the example from my mod:
I basically gave the three dusts different brightnesses; you might want to be more creative with your differences, depending on what you need.
Here is the end result of the dust in my mod:
Remember, to create the dust, just call your create method for the type of dust and provide the coordinates. Since the method returns the dust's index, you can customize it even more after you create it (i.e. if you want it to behave differently when produced from different sources). Feel free to ask any questions you have
Last edited: