local function NA_SpawnSkidDust(mo, radius)
	local particle
	particle = P_SpawnMobjFromMobj(mo, 0, 0, 0, MT_SPINDUST)
	local ranx = FixedMul(P_RandomRange(0, radius/FRACUNIT)*FRACUNIT,cos(P_RandomRange(0, 360)*ANG1))
	local rany = FixedMul(P_RandomRange(0, radius/FRACUNIT)*FRACUNIT,sin(P_RandomRange(0, 360)*ANG1))
	P_TeleportMove(particle, particle.x+ranx, particle.y+rany, particle.z)
	particle.tics = 10
	
	particle.destscale = (2*mo.scale)/2
	particle.scaled = particle.destscale
	P_SetObjectMomZ(particle, FRACUNIT, false)
	
	if (mo.eflags & (MFE_TOUCHWATER|MFE_UNDERWATER))
		particle.state = S_SPINDUST_BUBBLE1
	end
end

function A_NChase(actor, var1, var2) //No vars for now cuz lazy and no vanilla objects use vars
	if (actor.reactiontime)
		actor.reactiontime = $-1
	end
	if (actor.threshold)
		if (not actor.target or actor.target.health <= 0)
			actor.threshold = 0
		else
			actor.threshold = $-1
		end
	end
	if (not actor.target or not(actor.target.flags & MF_SHOOTABLE))
		// look for a new target
		if (P_LookForPlayers(actor, 0, true, false))
			return // got a new target
		end

		actor.state = actor.info.spawnstate
		return
	end
	if P_IsObjectOnGround(actor) //Jump off ledges code
		local momxy = actor.radius+5*FRACUNIT
		local momang = R_PointToAngle2(0, 0, actor.momx, actor.momy)
		if R_PointToDist2(0, 0, actor.momx, actor.momy) > FRACUNIT
			momang = R_PointToAngle2(0, 0, actor.momx, actor.momy)
		else
			if actor.target and actor.target.valid
				momang = R_PointToAngle2(actor.x, actor.y, actor.target.x, actor.target.y)
			else
				momang = actor.angle
			end
		end
		local addx = FixedMul(momxy, cos(momang))
		local addy = FixedMul(momxy, sin(momang))
		local goto = P_SpawnMobjFromMobj(actor, addx, addy, actor.z, MT_THOK)
		goto.tics = 2
		goto.fuse = 2
		goto.flags2 = $|MF2_DONTDRAW
		local gz = goto.floorz
		local lz = actor.floorz
		local downq = false
		if P_MobjFlip(actor) == 1
			gz = goto.floorz
			lz = actor.floorz
			if gz<lz
				downq = true
			end
		else
			gz = goto.ceilingz
			lz = actor.ceilingz
			if gz>lz
				downq = true
			end
		end
		local zdiff = abs(lz-gz)
		if downq and zdiff and zdiff > 100*FRACUNIT
		and R_PointToDist2(0, 0, actor.momx, actor.momy) > FRACUNIT*5
			P_SetObjectMomZ(actor, 7*FRACUNIT, true)
			S_StartSound(actor, sfx_s3k44)
			actor.jumped = true
			if actor.info.raisestate
				actor.prevstate = actor.state
				actor.state = actor.info.raisestate
			end
			return
		end
	end
		local factor = 8
		local angdiff
		if actor.target and actor.target.valid
			actor.movedir = -1
			local t = actor.target
			actor.targang = R_PointToAngle2(actor.x, actor.y, t.x, t.y)
			if not actor.hastarg
				if P_IsObjectOnGround(actor)
					P_SetObjectMomZ(actor, 5*FRACUNIT, true)
					actor.jumped = true
					actor.momx = 0
					actor.momy = 0
					local alart = P_SpawnMobjFromMobj(actor, 0, 0, 0, MT_GHOST)
					alart.fuse = TICRATE/2
					alart.target = actor
					alart.state = S_ALART1
					alart.spriteyoffset = actor.height + 25*FRACUNIT
					S_StartSound(alart, sfx_alart)
					if actor.info.seesound
						S_StartSound(actor, actor.info.seesound)
					end
					return
				end
				actor.turnto = actor.targang
			elseif P_IsObjectOnGround(actor)
				actor.addspeed = $ or 0
				local diff = abs(actor.targang-actor.angle)
				if diff > ANGLE_90
					actor.addspeed = 0
					if R_PointToDist2(0, 0, actor.momx, actor.momy) > actor.info.speed/4*3
						NA_SpawnSkidDust(actor, actor.radius)
					end
				elseif actor.addspeed < actor.info.speed*2
					actor.addspeed = $ + FRACUNIT
				end
				if R_PointToDist2(0, 0, actor.momx, actor.momy) > FRACUNIT*5
					if diff > ANG1*5
						actor.angle = R_PointToAngle2(0, 0, actor.momx, actor.momy)
					else
						actor.angle = actor.targang
					end
				else
					actor.turnto = actor.targang
				end
				if diff < (ANGLE_135+ANG30)
				and R_PointToDist2(0, 0, actor.momx, actor.momy) < actor.info.speed*3
					P_Thrust(actor, actor.targang, actor.info.speed+actor.addspeed) //Speedy
				end
				local ticspeed = ((actor.info.speed*2)-R_PointToDist2(0, 0, actor.momx, actor.momy))/FRACUNIT
				if ticspeed <= 0
					ticspeed = 1
				end
				actor.tics = ticspeed
			end
			actor.hastarg = true
		else
			actor.hastarg = false
		end
		if actor.turnto
			angdiff = (actor.turnto-actor.angle)
			if angdiff
				if angdiff > ANGLE_180
					angdiff = InvAngle(InvAngle(angdiff)/factor)
				else
					angdiff = $/factor
				end
				actor.angle = $+angdiff
				if abs(angdiff) < ANG15
					actor.turnto = 0
				end
			end
		end
	//Da missile shit
	local goto = false
	if (actor.flags2 & MF2_JUSTATTACKED)
		actor.flags2 = $ & ~MF2_JUSTATTACKED
		return
	end
	if ((not (var1 &1)) and actor.info.meleestate and P_CheckMeleeRange(actor))
		if (actor.info.attacksound)
			S_StartSound(actor, actor.info.attacksound)
		end
		actor.state = actor.info.meleestate
		//print("melee attack!")
		return
	end
	if (not (var1 &2) and actor.info.missilestate)
		if (actor.movecount or (not P_CheckMissileRange(actor)))
			goto = true
			//print("goto used")
		end
		if not goto
			//print("missile attack!")
			actor.state = actor.info.missilestate
			actor.flags2 = $|MF2_JUSTATTACKED
			return
		end
	end
	if goto
		//print("me when goto:")
		if (multiplayer and not actor.threshold and (actor.target.health <= 0 or not P_CheckSight(actor, actor.target))
		and P_LookForPlayers(actor, 0, true, false))
			return
		end
	end
	goto = false
end


freeslot(
	"MT_ELF",
		"SPR_ELF_",
		"S_ELF_1",
		"S_ELF_2",
		"S_ELF_3",
		"S_ELF_4",
		"S_ELF_5",
		"S_ELF_6",
		"S_ELF_JUMP1",
		"S_ELF_JUMP2",
		"sfx_elf1",
		"sfx_elf2"
)

states[S_ELF_1]={SPR_ELF_, A, 5,  A_Look, 0, 0, S_ELF_2}
states[S_ELF_2]={SPR_ELF_, A, 5,  A_Look, 0, 0, S_ELF_1}

states[S_ELF_3]={SPR_ELF_, A, 3,  A_NChase, 0, 0, S_ELF_4}
states[S_ELF_4]={SPR_ELF_, B, 3,  A_NChase, 0, 0, S_ELF_5}
states[S_ELF_5]={SPR_ELF_, C, 3,  A_NChase, 0, 0, S_ELF_6}
states[S_ELF_6]={SPR_ELF_, D, 3,  A_NChase, 0, 0, S_ELF_3}

states[S_ELF_JUMP1]={SPR_ELF_, E, 5,  A_PlaySound, sfx_elf2, 1, S_ELF_JUMP2}
states[S_ELF_JUMP2]={SPR_ELF_, E, 5,  A_ZThrust, -1, 0, S_ELF_JUMP2}

mobjinfo[MT_ELF]={
	doomednum = 1573,	
	deathstate = S_TNTBARREL_EXPL1,	
	spawnstate = S_ELF_1,
	seestate = S_ELF_3,
	seesound = sfx_elf1,
	spawnhealth = 1,
	reactiontime = 32,
	painchance = 170,
	speed = 7*FRACUNIT, //Speedy boi
	mass = 100, //5 = he fuckin flies
	damage = 1,
	radius = 16*FRACUNIT,
	height = 64*FRACUNIT,	
	raisestate = S_ELF_JUMP1,
	flags = MF_ENEMY|MF_SPECIAL|MF_SHOOTABLE
}

addHook("MobjThinker", function(mo)
	if mo and mo.valid
	and mo.type == MT_ELF
		if not (mo.flags & MF_NOGRAVITY)
			mo.falltime = $ or 0
			if P_IsObjectOnGround(mo) //Fall damage be like
				if mo.deathfall
					P_DamageMobj(mo, nil, nil, DMG_INSTAKILL)
				end
				if P_MobjFlip(mo) == 1
					mo.lastfloorz = mo.floorz
				else
					mo.lastfloorz = mo.ceilingz
				end
				mo.falltime = 0
				if mo.falling
					mo.jumped = false
				end
				if mo.info.raisestate
				and mo.prevstate
				and not mo.deathfall
					mo.state = mo.prevstate
				end
				mo.falling = false
			else
				mo.falling = true
				if P_MobjFlip(mo) == 1
					mo.fallfloorz = mo.floorz
				else
					mo.fallfloorz = mo.ceilingz
				end
				local fz = 0
				if mo.fallfloorz
					fz = mo.fallfloorz
				end
				local lz = 0
				if mo.lastfloorz
					lz = mo.lastfloorz
				end
				if abs(fz-lz) > 500*FRACUNIT
					mo.deathfall = true
				else
					mo.deathfall = false
				end
				local FixAng = FixedAngle(mo.momz*4*P_MobjFlip(mo))
				if mo.jumped
				and mo.momz*P_MobjFlip(mo) >= 0
					mo.spriteyscale = FRACUNIT + FixedMul(FRACUNIT/3, sin(FixAng))
					mo.spritexscale = FRACUNIT - FixedMul(FRACUNIT/3, sin(FixAng))
				else
					mo.spriteyscale = FRACUNIT
					mo.spritexscale = FRACUNIT
				end
			end
		end
	end
end)