How would i make an NPC try to attack the player when the player goes within around maybe seven studs?
I know it involves magnitude but i’m not sure how i would make the npc walk towards the player, to then attack it.
How would i make an NPC try to attack the player when the player goes within around maybe seven studs?
I know it involves magnitude but i’m not sure how i would make the npc walk towards the player, to then attack it.
You can use Humanoid:MoveTo
. Give the position of the HumanoidRootPart
as the first and the HumanoidRootPart
as the second argument. Use Humanoid.MoveToFinished
to detect when the timeout is reached and repeat the MoveTo
call.
To make sure that the NPC only follows when it’s close enough, check the magnitude every frame.
I haven’t tested this code, so I’m not sure if it works.
local RunService = game:GetService("RunService")
local Players = game:GetService("Players")
local FOLLOW_MAX_DISTANCE = 7
local npc = -- npc here
local plrChars = {}
local plrConns = {}
local function onCharAdded(char)
plrChars[#plrChars+1] = char
end
local function onCharRemoving(char)
table.remove(plrChars, table.find(plrChars, char)
end
local function onPlayerAdded(plr)
local conns = {}
conns[1] = plr.CharacterAdded:Connect(onCharacterAdded)
conns[2] = plr.CharacterRemoving:Connect(onCharacterRemoving)
plrConns[plr] = conns
end
local function onplrRemoving(plr)
for i, v in ipairs(plrConns[plr]) do
v:Disconnect()
end
plrConns[plr] = nil
end
local function isCloseEnough(npc, plrChar)
local distance = (npc.HumanoidRootPart.Position-plrChar.HumanoidRootPart.Position).Magnitude
if distance <= FOLLOW_MAX_DISTANCE
return distance
end
end
local function randDirNum()
return math.random()*(-1)^math.random(1, 2)
end
local function getRandomDirection()
local direction = Vector3.new(randDirNum(), 0, randDirNum())
if direction == Vector3.new() then
direction = direction = getRandomDirection()
end
direction = direction.Unit
return direction
end
local function randomMovement(npc)
local hum = npc.Humanoid
local direction = getRandomDirection()
hum:MoveTo(npc.HumanoidRootPart.Position+direction*hum.WalkSpeed*8)
end
local function moveToWardsPlr(npc, plrChar)
local plrHrp = plrChar.HumanoidRootPart
npc.Humanoid:MoveTo(plrHrp.Position, plrHrp)
end
local function findClosestChar(npc)
local closestChar, closestDistance
for i, char in ipairs(plrChars) do
local distance = isCloseEnough(char)
if distance and not closestChar or distance < closestDistance then
closestChar = char
closestDistance = distance
end
end
return closestChar
end
local function handleMovement(npc)
local hum = npc.Humanoid
local moving = false
local conn =
hum.MoveToFinished:Connect(function()
moving = false
end
while npc.Parent and hum.Health > 0 do
local closestChar = findClosestChar(npc)
if not closestChar and (isFollowing or not moving) then
randomMovement(npc)
isFollowing = nil
isMoving = true
elseif closestChar and (closestChar ~= isFollowing or not moving) then
moveTowardsPlr(npc, closestChar)
isFollowing = closestChar
isMoving = true
end
RunService.Heartbeat:Wait()
end
conn:Disconnect()
end
Players.PlayerAdded:Connect(onPlayerAdded)
Players.PlayerRemoving:Connect(onPlayerRemoving)
handleMovement(npc)