Rewrote AI of the Core Spider (wall).

This commit is contained in:
FyloZ 2020-07-06 15:18:38 -04:00
parent aa893193de
commit c8b07494c3
3 changed files with 115 additions and 24 deletions

View File

@ -1,5 +1,6 @@
using System;
using Decimation.Content.Tiles.ShrineoftheMoltenOne;
using Decimation.Lib.Util;
using Microsoft.Xna.Framework;
using Terraria;
using Terraria.ID;
@ -36,11 +37,14 @@ namespace Decimation.Content.NPCs
npc.lifeMax = 750;
npc.knockBackResist = 0.25f;
npc.lavaImmune = true;
npc.value = 7000;
npc.buffImmune[20] = true;
npc.buffImmune[31] = false;
npc.buffImmune[BuffID.OnFire] = true;
npc.buffImmune[BuffID.Burning] = true;
npc.timeLeft = NPC.activeTime * 2;
npc.HitSound = SoundID.NPCHit19;
npc.DeathSound = SoundID.NPCDeath12;
}
public override void FindFrame(int frameHeight)
@ -54,6 +58,12 @@ namespace Decimation.Content.NPCs
}
}
public override bool PreAI()
{
Lighting.AddLight(npc.Center, LightingUtils.Rgb255ToRgb1(255, 155, 48));
return true;
}
public override void AI()
{
if (npc.target >= 255) npc.TargetClosest();

View File

@ -1,4 +1,5 @@
using Decimation.Content.Tiles.ShrineoftheMoltenOne;
using Decimation.Lib.Util;
using Microsoft.Xna.Framework;
using Terraria;
using Terraria.ID;
@ -9,43 +10,115 @@ namespace Decimation.Content.NPCs
// Check line 43861 of NPC.cs
internal class CoreSpiderWall : ModNPC
{
private int frame;
private readonly int shootFrame = 120;
private const int AnimationFps = 10;
private const int AnimationFrameCount = 4;
private const float Speed = 2;
private const int ShootInterval = 120;
private int _frame;
public override void SetStaticDefaults()
{
DisplayName.SetDefault("Core Spider");
Main.npcFrameCount[npc.type] = 4;
Main.npcFrameCount[npc.type] = AnimationFrameCount;
}
public override void SetDefaults()
{
npc.CloneDefaults(NPCID.BlackRecluseWall);
npc.width = 60;
npc.height = 62;
npc.width = 52;
npc.height = 52;
npc.aiStyle = -1;
npc.lifeMax = 750;
animationType = NPCID.BlackRecluseWall;
npc.knockBackResist = 0.25f;
npc.lavaImmune = true;
npc.value = 7000;
npc.buffImmune[20] = true;
npc.buffImmune[31] = false;
npc.buffImmune[BuffID.OnFire] = true;
npc.buffImmune[BuffID.Burning] = true;
npc.timeLeft = NPC.activeTime * 2;
npc.noGravity = true;
npc.HitSound = SoundID.NPCHit19;
npc.DeathSound = SoundID.NPCDeath12;
}
public override bool PreAI()
{
Lighting.AddLight(npc.Center, LightingUtils.Rgb255ToRgb1(255, 155, 48));
return true;
}
public override void AI()
{
int x = (int) npc.Center.X / 16;
int y = (int) npc.Center.Y / 16;
bool onWall = true;
for (int i = x - 1; i <= x + 1; i++)
for (int j = y - 1; j <= y + 1; j++)
if (Main.tile[i, j].wall <= 0)
onWall = false;
if (npc.target >= 255) npc.TargetClosest();
Player target = Main.player[npc.target];
if (npc.Distance(target.position) > 480) npc.target = 255;
if (!Collision.CanHitLine(npc.position, npc.width, npc.height, target.position, target.width, target.height)
) npc.target = 255;
bool hasTarget = npc.target < 255 && target.active && !target.dead;
if (Main.expertMode)
// Rotation
if (hasTarget)
{
if (frame >= shootFrame)
Vector2 distance = target.Center - npc.Center;
if (distance.Length() > 0)
{
if (Main.rand.Next(3) == 0)
float rotation = distance.ToRotation();
npc.rotation = rotation;
}
}
else
{
npc.rotation += Main.rand.NextFloat(-0.05f, 0.05f);
}
Vector2 velocity = new Vector2(1, 0);
velocity.Normalize();
velocity *= Speed;
npc.velocity = velocity.RotatedBy(npc.rotation);
if (!hasTarget)
{
Vector2 frontTilePosition = npc.Center;
frontTilePosition += new Vector2(npc.width / 2f + 16, 0).RotatedBy(npc.rotation);
int frontTileX = (int) frontTilePosition.X / 16;
int frontTileY = (int) frontTilePosition.Y / 16;
Tile frontTile = Main.tile[frontTileX, frontTileY];
Tile frontTileY1 = Main.tile[frontTileX, frontTileY + 1];
Tile frontTileY2 = Main.tile[frontTileX, frontTileY - 1];
if (frontTile == null) frontTile = new Tile();
if (frontTileY1.nactive() && Main.tileSolid[frontTileY1.type] &&
!Main.tileSolidTop[frontTileY1.type] &&
(!frontTileY2.nactive() || !Main.tileSolid[frontTileY2.type] ||
Main.tileSolidTop[frontTileY2.type]))
npc.rotation += MathHelper.PiOver2;
else if (frontTileY2.nactive() && Main.tileSolid[frontTileY2.type] &&
!Main.tileSolidTop[frontTileY2.type] &&
(!frontTileY1.nactive() || !Main.tileSolid[frontTileY1.type] ||
Main.tileSolidTop[frontTileY1.type]))
npc.rotation -= MathHelper.PiOver2;
else if (frontTile.nactive() && Main.tileSolid[frontTile.type] && !Main.tileSolidTop[frontTile.type])
npc.rotation += MathHelper.Pi;
}
int currentTileX = (int) npc.Center.X / 16;
int currentTileY = (int) npc.Center.Y / 16;
bool onWall = false;
for (int x = currentTileX - 1; x <= currentTileX + 1; x++)
{
for (int y = currentTileY - 1; y <= currentTileY + 1; y++)
{
if (Main.tile[x, y].wall > 0) onWall = true;
}
}
if (!onWall) npc.Transform(ModContent.NPCType<CoreSpider>());
if (Main.expertMode && hasTarget)
{
if (_frame >= ShootInterval)
{
if (Main.rand.Next(4) == 0)
{
Vector2 mouthPos = npc.Center + new Vector2(npc.width / 2f, 0).RotatedBy(npc.rotation);
Vector2 projSpeed = new Vector2(5, 0).RotatedBy(npc.rotation);
@ -53,18 +126,26 @@ namespace Decimation.Content.NPCs
Projectile.NewProjectile(mouthPos, projSpeed, ProjectileID.Fireball, 130, 30);
}
frame = 0;
_frame = 0;
}
else
{
frame++;
_frame++;
}
}
if (!onWall)
npc.Transform(ModContent.NPCType<CoreSpider>());
else
base.AI();
if (npc.spriteDirection == -1) npc.spriteDirection = 1;
}
public override void FindFrame(int frameHeight)
{
if (++npc.frameCounter >= 60f / AnimationFps)
{
npc.frameCounter = 0;
npc.frame.Y += frameHeight;
if (npc.frame.Y / frameHeight >= AnimationFrameCount) npc.frame.Y = 0;
}
}
public override bool CheckConditions(int left, int right, int top, int bottom)

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.8 KiB

After

Width:  |  Height:  |  Size: 2.2 KiB