Standalone [1.3] tModLoader - A Modding API

How whould see the out the Set Defaults for an NPC with these Sprite?
View attachment 110323
I dont get the Animaton to work,in Some Animations He Disappers or there is the little Part of the Legs over him
I opened your file up. It's 740 pixels tall, but 13 frames. 740/13 isn't a whole number. It looks like you were going for 55 pixels tall with the default 2 pixel borders, but your spacing is off.
97Offxd.png

[doublepost=1463293814,1463293710][/doublepost]
um i did some eclipce coding and i made some bosses i just am trying to learn hoe to make an npc
If you are thinking of using a vanilla ai, it's as easy as Party Zombie in example mod, but if you are doing your own AI, it is really hard.
 
Just hoping someone could answe @Zocklukas' question, it'd be much appreciated!
Thats currently was uselesw,beecause he already maked an new Sprite C;
I opened your file up. It's 740 pixels tall, but 13 frames. 740/13 isn't a whole number. It looks like you were going for 55 pixels tall with the default 2 pixel borders, but your spacing is off.
97Offxd.png

[doublepost=1463293814,1463293710][/doublepost]
If you are thinking of using a vanilla ai, it's as easy as Party Zombie in example mod, but if you are doing your own AI, it is really hard.

How these Sprite Animation Part in the setdeuaflts looks like?
LoneTrapper.png
 
Thats currently was uselesw,beecause he already maked an new Sprite C;


How these Sprite Animation Part in the setdeuaflts looks like?
View attachment 110487
If you are doing a town NPC, it'll look like how Example Person looks. The easiest would be to model your frames after a vanilla town npc texture and use the same values. Also use the animationType = NPCID.???; for the type you are mimicking. If that doesn't answer your question, maybe I'm not understanding what you are having questions about.
 
Anyone know how I can make a projectile heal the player when it hits an NPC?

Try adding this to your weapon.cs

public override void OnHitNPC(Player player, NPC target, int damage, float knockback, bool crit)
{
player.statLife += 5; //The heal amount.
player.HealEffect(5); //Shows how much it healed the player above his head.
}
 
If you are doing a town NPC, it'll look like how Example Person looks. The easiest would be to model your frames after a vanilla town npc texture and use the same values. Also use the animationType = NPCID.???; for the type you are mimicking. If that doesn't answer your question, maybe I'm not understanding what you are having questions about.

1.I dont maked the Sprite,i got them From another one and should make it
2.I can you say me how the

Code:
Main.npcFrameCount[npc.type] = 26;
            NPCID.Sets.ExtraFramesCount[npc.type] = 9;
            NPCID.Sets.AttackFrameCount[npc.type] = 4;
            NPCID.Sets.DangerDetectRange[npc.type] = 700;
            NPCID.Sets.AttackType[npc.type] = 0;
            NPCID.Sets.AttackTime[npc.type] = 90;
            NPCID.Sets.AttackAverageChance[npc.type] = 30;
            animationType = NPCID.Guide;

Is for

An Wizard
 
Can we control how often does a buff do something in the buff.cs?
For e.g. the buff heals or damages only every second once.
 
Last edited:
Usually the frame is what determines the state of a tile. A variable won't work since all tiles of a type share the same class. The music boxes and fountains all work that way.
I'm not quite sure what to do though. When one player turns the jukebox on, its animation changes - but again only for the one player...
This is what I've got if it's of any use:
Code:
public class Jukebox_Tile : ModTile
    {
        public static bool inUse = false;
        public static bool alreadyPlaying = false;

        public override void SetDefaults()
        {
            Main.tileFrameImportant[Type] = true;
            Main.tileNoAttach[Type] = true;
            Main.tileLavaDeath[Type] = true;
            TileObjectData.newTile.CopyFrom(TileObjectData.Style2xX);
            TileObjectData.newTile.Width = 2;
            TileObjectData.newTile.Height = 3;
            TileObjectData.newTile.StyleHorizontal = true;
            TileObjectData.newTile.CoordinateHeights = new int[] {16,16,16};
            TileObjectData.newTile.CoordinateWidth = 16;
            TileObjectData.newTile.CoordinatePadding = 0;
            TileObjectData.addTile(Type);
            AddMapEntry(new Color(255, 71, 19), "Jukebox");
            animationFrameHeight = 48;
        }

        public override void AnimateTile(ref int frame, ref int frameCounter)
        {
            if (!inUse)
            {
                frame = 0;
                return;
            }
            if (++frameCounter == 12)
            {
                if (frame == 9) frame = 1; else frame++;
                frameCounter = 0;
            }
        }

        public override void RightClick(int i, int j)
        {
            inUse = !inUse;
            if (alreadyPlaying) alreadyPlaying = !alreadyPlaying;
        }

        public override void NearbyEffects(int i, int j, bool closer)
        {
            Player player = Main.player[Main.myPlayer];
            if (closer) {
                ((Jukebox_ModPlayer)player.GetModPlayer(mod, "Jukebox_ModPlayer")).closeToJukebox = true;
                if (inUse)
                    ((Jukebox_ModPlayer)player.GetModPlayer(mod, "Jukebox_ModPlayer")).setJukebox(true,JukeboxMod.randomNumber);
            }
            else
                ((Jukebox_ModPlayer)player.GetModPlayer(mod, "Jukebox_ModPlayer")).closeToJukebox = false;
        }
    }
Code:
   public class JukeboxMod : Mod
    {

        public static int randomNumber = 0;
        [...]

        public JukeboxMod()
        {
            Properties = new ModProperties()
            {
                Autoload = true,
                AutoloadGores = true,
                AutoloadSounds = true
            };
        }

        public override void UpdateMusic(ref int music)
        {
            if (Main.myPlayer != -1 && !Main.gameMenu)
            {
                if (Main.player[Main.myPlayer].active && Tiles.Jukebox_Tile.inUse == true)
                {
                    if (!((Jukebox_ModPlayer)Main.player[Main.myPlayer].GetModPlayer(this, "Jukebox_ModPlayer")).closeToJukebox)
                    {
                        Tiles.Jukebox_Tile.inUse = false;
                        Tiles.Jukebox_Tile.alreadyPlaying = false;
                    }else {
                        if (Tiles.Jukebox_Tile.alreadyPlaying == false)
                        {
                            randomNumber = Main.rand.Next(jukeboxSongs.Length);
                            Main.NewText("Currently playing: " + songNames[randomNumber]);
                            Tiles.Jukebox_Tile.alreadyPlaying = true;
                        }
                        music = this.GetSoundSlot(SoundType.Music, jukeboxSongs[randomNumber]);
                    }
                }
            }
        }
    }
Code:
class Jukebox_ModPlayer : ModPlayer
    {
        public bool closeToJukebox = false;

        public void setJukebox(bool state,int number)
        {
            JukeboxMod.randomNumber = number;
            Tiles.Jukebox_Tile.inUse = state;
        }
    }
I know, it's a long mess by now..
 
Last edited:
Can we control how often does a buff do something in the buff.cs?
For e.g. the buff heals or damages only every second once.

Buffs are updated every frame, and there are 60 frames in one second. So if you get a counter that does something on every 60th frame, you've got a 'once per second' effect.

Pseudo-code:
Code:
if(frameCount%60 == 0)
{
   Effect();
   frameCount = 0;
}
frameCount++;
 
Buffs are updated every frame, and there are 60 frames in one second. So if you get a counter that does something on every 60th frame, you've got a 'once per second' effect.

Pseudo-code:
Code:
if(frameCount%60 == 0)
{
   Effect();
   frameCount = 0;
}
frameCount++;

But then it gives these errors:

The name 'frameCount' does not exist in the current context
The name 'Effect' does not exist in the current context

Do I need to create the "frameCount" and "Effect" variables, and if yes how?
 
But then it gives these errors:

The name 'frameCount' does not exist in the current context
The name 'Effect' does not exist in the current context

Do I need to create the "frameCount" and "Effect" variables, and if yes how?

Yes, you have to declare frameCount as a field. Effects was just a placeholder for your actual effect code.
 
Yes, you have to declare frameCount as a field. Effects was just a placeholder for your actual effect code.

So for e.g.

public override void Update(Player player, ref int buffIndex)
{
if(frameCount%60 == 0)
{
player.statLife += 2;
frameCount = 0;

}
frameCount++;
}

But how do I declare the frameCount as a field.
 
So for e.g.

public override void Update(Player player, ref int buffIndex)
{
if(frameCount%60 == 0)
{
player.statLife += 2;
frameCount = 0;

}
frameCount++;
}

But how do I declare the frameCount as a field.

https://msdn.microsoft.com/en-us/library/ms173118.aspx

You also probably want to include an if statement to check if you're going over the health limit. Not mandatory, I believe, but it's good practice to do so.
 
I'm not quite sure what to do though. When one player turns the jukebox on, its animation changes - but again only for the one player...
This is what I've got if it's of any use:
Code:
public class Jukebox_Tile : ModTile
    {
        public static bool inUse = false;
        public static bool alreadyPlaying = false;

        public override void SetDefaults()
        {
            Main.tileFrameImportant[Type] = true;
            Main.tileNoAttach[Type] = true;
            Main.tileLavaDeath[Type] = true;
            TileObjectData.newTile.CopyFrom(TileObjectData.Style2xX);
            TileObjectData.newTile.Width = 2;
            TileObjectData.newTile.Height = 3;
            TileObjectData.newTile.StyleHorizontal = true;
            TileObjectData.newTile.CoordinateHeights = new int[] {16,16,16};
            TileObjectData.newTile.CoordinateWidth = 16;
            TileObjectData.newTile.CoordinatePadding = 0;
            TileObjectData.addTile(Type);
            AddMapEntry(new Color(255, 71, 19), "Jukebox");
            animationFrameHeight = 48;
        }

        public override void AnimateTile(ref int frame, ref int frameCounter)
        {
            if (!inUse)
            {
                frame = 0;
                return;
            }
            if (++frameCounter == 12)
            {
                if (frame == 9) frame = 1; else frame++;
                frameCounter = 0;
            }
        }

        public override void RightClick(int i, int j)
        {
            inUse = !inUse;
            if (alreadyPlaying) alreadyPlaying = !alreadyPlaying;
        }

        public override void NearbyEffects(int i, int j, bool closer)
        {
            Player player = Main.player[Main.myPlayer];
            if (closer) {
                ((Jukebox_ModPlayer)player.GetModPlayer(mod, "Jukebox_ModPlayer")).closeToJukebox = true;
                if (inUse)
                    ((Jukebox_ModPlayer)player.GetModPlayer(mod, "Jukebox_ModPlayer")).setJukebox(true,JukeboxMod.randomNumber);
            }
            else
                ((Jukebox_ModPlayer)player.GetModPlayer(mod, "Jukebox_ModPlayer")).closeToJukebox = false;
        }
    }
Code:
   public class JukeboxMod : Mod
    {

        public static int randomNumber = 0;
        [...]

        public JukeboxMod()
        {
            Properties = new ModProperties()
            {
                Autoload = true,
                AutoloadGores = true,
                AutoloadSounds = true
            };
        }

        public override void UpdateMusic(ref int music)
        {
            if (Main.myPlayer != -1 && !Main.gameMenu)
            {
                if (Main.player[Main.myPlayer].active && Tiles.Jukebox_Tile.inUse == true)
                {
                    if (!((Jukebox_ModPlayer)Main.player[Main.myPlayer].GetModPlayer(this, "Jukebox_ModPlayer")).closeToJukebox)
                    {
                        Tiles.Jukebox_Tile.inUse = false;
                        Tiles.Jukebox_Tile.alreadyPlaying = false;
                    }else {
                        if (Tiles.Jukebox_Tile.alreadyPlaying == false)
                        {
                            randomNumber = Main.rand.Next(jukeboxSongs.Length);
                            Main.NewText("Currently playing: " + songNames[randomNumber]);
                            Tiles.Jukebox_Tile.alreadyPlaying = true;
                        }
                        music = this.GetSoundSlot(SoundType.Music, jukeboxSongs[randomNumber]);
                    }
                }
            }
        }
    }
Code:
class Jukebox_ModPlayer : ModPlayer
    {
        public bool closeToJukebox = false;

        public void setJukebox(bool state,int number)
        {
            JukeboxMod.randomNumber = number;
            Tiles.Jukebox_Tile.inUse = state;
        }
    }
I know, it's a long mess by now..
I already told you that you don't do this with booleans, you do it with the frame of the tile. Example: https://github.com/bluemagic123/tModLoader/blob/master/ExampleMod/Tiles/VoidMonolith.cs
[doublepost=1463316251,1463316182][/doublepost]
How do I do that? I'm sorry, I don't have a lot of experience when it comes to coding :p
Example Person does that: https://github.com/bluemagic123/tModLoader/blob/master/ExampleMod/NPCs/ExamplePerson.cs#L175

Also, is this what you are actually asking? Rotating the inventory that is sold depending on the day?
 
Try adding this to your weapon.cs

public override void OnHitNPC(Player player, NPC target, int damage, float knockback, bool crit)
{
player.statLife += 5; //The heal amount.
player.HealEffect(5); //Shows how much it healed the player above his head.
}
I've tried that already in both my weapon's .cs and my projectile's .cs, but neither work. I only got it to work for the melee weapon, because it appears to only work if contact weapons.
 
Change

Code:
public override void OnHitNPC(Player player, NPC target, int damage, float knockback, bool crit)

to

Code:
public override void OnHitNPC(NPC target, int damage, float knockback, bool crit)
 
Change

Code:
public override void OnHitNPC(Player player, NPC target, int damage, float knockback, bool crit)

to

Code:
public override void OnHitNPC(NPC target, int damage, float knockback, bool crit)

That gives me "OnHitNPC(Terraria.NPC, int, float, bool)': no suitable method found to override"
 
Well,sry on my Projectiles its smple works
or try to Remove
NPC target,
If it helps, I'll post my code to see if I'm missing something simple.
Code:
using System;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Graphics;
using Terraria;
using Terraria.ID;
using Terraria.ModLoader;

namespace ModName.Projectiles
{
    public class ProjectileName : ModProjectile
    {
        public override void SetDefaults()
        {
            projectile.CloneDefaults(ProjectileID.PoisonedKnife);
            projectile.name = "Projectile";
            projectile.width = 14;
            projectile.height = 28;
        }
        public override void OnHitNPC(NPC target, int damage, float knockback, bool crit)
        {
            player.statLife += 5;
            player.HealEffect(5);
        }
    }
}
 
Back
Top Bottom