How to fix pathfinding jittering?

I’m trying to make a nextbot game, but I’m having a ton of trouble getting the pathfinding to work smoothly. Instead of moving smoothly the nextbot jitters back and forth while moving, I know that this is from overlapping :MoveTo() functions, but I can’t find a fix anywhere.

Here’s the part of the code that is responsible for pathfinding:

local function pathFindToPos(nextbot, pos)
	local path = pathfindingService:ComputeSmoothPathAsync(nextbot.PrimaryPart.Position, pos, 512)
	local waypoints = path:GetWaypoints()
	local hum = nextbot.Humanoid
	local data = info_nextbots[nextbot]
	
	if waypoints then
		for index, point in pairs(waypoints) do
			hum:MoveTo(point.Position)

			data.CurrentWayPoint = point.Position

			hum.MoveToFinished:Wait()
		end
	end
end


setUpAll()

game["Run Service"].Heartbeat:Connect(function()
	for nextbot, data in pairs(info_nextbots) do
		pathFindToPos(nextbot, workspace.TestPart.Position)
	end
end)

And even if I did fix it I don’t want it to look unnatural and robotic.

  1. Use RunService.Stepped

  2. Set NetworkOwnership to the Server

HumanoidRootPart:SetNetworkOwner(nil)

Ok, I tried that but it’s still jittering.

Why are you calculating a new path every frame. It makes no sense to do this so frequently and is the most likely cause of your problem. You are never going to reach the first waypoint in a single frame, never mind the rest of the waypoints generated.

The player is gonna be constantly moving and I want the nextbot to always be following the player’s current position, not where they were.

That answer still makes no sense. How far (in studs) do you expect the player to move in one single frame? Secondly, you are attempting to iterate over all waypoints according your waypoints loop.

You need to consider the nextbot damage range , the nextbots speed and the player speed. A factor of these variables will then give you the frequency to repeat your ComputePath. I can guarantee that it won’t be every frame.

You could probably tune the frequency down to every 0.5 second, massively improve performance and have no discernible impact on the nextbot pathing ability.

Try removing the RenderStepped loop. You should have a task.wait(0.5) loop instead so it wont recalculate that many times.

I guess I didn’t think about that. :sweat_smile: I’ve only been scripting small things so I still have almost no idea what I’m doing tbh. And @BandQueenForever I tried the task.wait() loop but when I move the part around the nextbot goes to where the part was.
Here’s the part that I changed:

while task.wait(0.5) do
	for nextbot, data in pairs(info_nextbots) do
		pathFindToPos(nextbot, workspace.TestPart.Position)
	end
end

And since there is the Humanoid.WalkToFinished:Wait() in the pathFindToPos() it doesn’t recalculate until the path is finished. So how do you cancel the currently running pathfinding when a new path is calculated?

I don’t think you can and I don’t think it’s needed because there’ll be a delay but if you really want to, perhaps you can try looking at coroutines. I haven’t learned much about them but maybe they’ll help you: coroutine | Roblox Creator Documentation

I messed with coroutines, and it completely broke it. Nothing after or inside the pathFindToPos() will run.

local current

local function pathFindToPos(nextbot, pos)
	
	
	current = coroutine.create(function()
		local path = pathfindingService:FindPathAsync(nextbot.PrimaryPart.Position, pos, 512)
		local waypoints = path:GetWaypoints()
		local hum = nextbot.Humanoid
		local data = info_nextbots[nextbot]

		if waypoints then
			for index, point in pairs(waypoints) do
				hum:MoveTo(point.Position)

				data.CurrentWayPoint = point.Position

				hum.MoveToFinished:Wait()
			end
		end
	end)
	coroutine.resume(current)
end

setUpAll()--ignore

game["Run Service"].Heartbeat:Connect(function()
	for index, nextbot in pairs(info_nextbots) do
		if nextbot.CurrentWayPoint then
			nextbot.DebugPart.Position = nextbot.CurrentWayPoint
			local pathPart = nextbot.DebugPart:Clone()
			pathPart.Parent = workspace
			pathPart.Color = Color3.fromRGB(37, 255, 21)
			pathPart.Name = "PathPart"
			pathPart.Size = Vector3.new(.5,.5,.5)
		end
	end
end)

while task.wait(0.25) do
	for nextbot, data in pairs(info_nextbots) do
		coroutine.yield(current)
		print("test2")
		pathFindToPos(nextbot, workspace.TestPart.Position)
	end
end