The pathfinding zombies in my game are moving almost robotically. Can anyone help?
Part of my script that handles the pathfinding:
task.spawn(function()
wait(15)
if clone.Parent ~= nil then
print("Zombie has escaped!")
clone:Destroy()
local char = player.Character or player.CharacterAdded:Wait()
local zombieClone = zombie:Clone()
zombieClone.Parent = folder
zombieClone.HumanoidRootPart:SetNetworkOwner(nil)
RS.Heartbeat:Connect(function()
if zombieClone:FindFirstChild("HumanoidRootPart") and (char ~= nil) and zombie:FindFirstChildOfClass("Humanoid" then
local path = PFS:CreatePath({
AgentRadius = 2,
AgentHeight = 5,
AgentCanJump = false,
AgentCanClimb = false,
WaypointSpacing = 1
})
path:ComputeAsync(zombieClone.HumanoidRootPart.Position, char.HumanoidRootPart.Position)
local waypoints = path:GetWaypoints()
for i, point in pairs(waypoints) do
zombieClone.Humanoid:MoveTo(point.Position)
zombieClone.Humanoid.MoveToFinished:Wait()
end
end
end)
end
end)
Could you provide a video of the zombie attempting to pathfind?
Without having that, I would guess your problem is how many waypoint tables you are iterating through at once. Since you are iterating through the waypoints generated inside of the heartbeat connection, it seems like your zombie is trying to pursue multiple waypoints at once which will lead to severe stuttering as well as (I assume) really bad performance.
It’s all in the Waypoint spacing and the timing between. Try to line that up so they hit at the same time to avoid stuttering. I also believe the better choice is Stepped in cases like this.
Heartbeat is not limited to the frame rate and usually fires at a higher frequency, around 200 times per second or more, depending on the system’s performance.
Stepped is tied to the frame rate, which is typically 60 times per second.
At 60 times a seconds this is even overkill here.
Due to how :MoveTo() works, it is only moving toward one waypoint (it pursues the last :MoveTo() function ran) but the stutters are likely from the other waypoint iterations also calling :MoveTo() prior to the final function use.
There are two approaches for using pathfinding toward a moving target (that I’m aware of, there may be more): a repetitve approach where you constantly generate a new path and follow the first waypoint, and a partial path method where you generate a path and only utilize the first few waypoints and generate a new path once those are all traversed.
The repetitive approach is easier to implement and is what your existing zombie appears to try to use. To have your zombie properly utilize this pathfinding method, you should first move the section of code that calls :MoveTo() out of the heartbeat connection and create a new method of moving the zombie to utilize the most recently generated path and overriding it when a new one is generated while making sure the portion that moves the zombie reacts accordingly. I don’t personally utilize this method of pathfinding so some of my advice here may be incorrect so be sure to experiment with this all. A module here on devforum that utilizes this method of pathfinding that you can study/read through is “SimplePath”.
Also, using a heartbeat connection to generate paths is very excessive. You can use a normal while loop to generate a path and update the waypoint table without a task.wait() as the :ComputeAsync() function yields. You should check the status of the path as well to prevent any errors and handle failed path generation.
You can either have the zombie roam briefly since a failure is likely to happen if the player is in an unreachable location or anything else you’d like. As long as you have something in mind you want the zombie to do if a player isn’t reachable, it is likely to be possible.
In this one you can see they reaching the waypoint with time to spare. Try guessing different options till you find a sweet spot. Hard to say without being able to test this. Looked at one of mine it doesn’t re-fire the path as much and is also re-firing at the path 1/2 way point, until close to the target.