Speed Anti Cheat Expected Distance Calculation Incorrect

You can write your topic however you want, but you need to answer these questions:

  1. What do you want to achieve? Keep it simple and clear!
    I want my speed anticheat to work.

  2. What is the issue? Include screenshots / videos if possible!
    I’m pretty sure the issue is that the player’s actual distance travelled is different from my calculated distance because of some unknown variable. I’m hoping one of you guys knows the problem!

  3. What solutions have you tried so far? Did you look for solutions on the Developer Hub?
    I’ve tried putting print statements everywhere, and deduced that the issue is how distance without leniency is being calculated. Pretty sure it might be ping, not sure how to fix it though.

This is the code for the speed check module:

local Settings = require(script.Parent.Parent.Settings)

local function check(character, deltaTime, previousPosition)
	local hrp = character.HumanoidRootPart
	local hrpPos = hrp.Position

	local walkSpeed = character.Humanoid.WalkSpeed
	
	if previousPosition == Vector3.new(0, 0, 0) then
		return false
	end
	
	local distanceTravelled = (hrpPos - previousPosition).Magnitude
	local expectedDistancePlusLeniency = (walkSpeed + Settings.SpeedLeniency) * deltaTime
	
	if distanceTravelled > expectedDistancePlusLeniency then
		print(walkSpeed * deltaTime) -- distance without leiniency
		print(distanceTravelled) -- actual distance
		print(expectedDistancePlusLeniency) -- 
		return true
	end

	return false
end

return check

Code for script requiring the module:

local Players = game:GetService("Players")
local ServerScriptService = game:GetService("ServerScriptService")
local RunService = game:GetService("RunService")

local Settings = require(ServerScriptService.Settings)

local checks = {}
for _, check in ipairs(ServerScriptService.Checks:GetChildren()) do
	if Settings.EnabledChecks[check.Name] then
		local callback = require(check)
		checks[check] = callback
	end
end

--local Template = {
--	SteppedConnection = nil,
--	lastPosition = nil,
--}



Players.PlayerAdded:Connect(function(player)


	player.CharacterAdded:Connect(function(character)
		-- disconnect these events when the player leaves
		local previousPosition = Vector3.new(0, 0, 0)
		
		RunService.Stepped:Connect(function(time, deltaTime)

			for _, check in pairs(checks) do
				local playerUnsuspicious = check(character, deltaTime, previousPosition)

				if playerUnsuspicious then
					-- teleport them back to previous position, kicks for now
					player:Kick()
				end
			end
			
			previousPosition = character.HumanoidRootPart.Position
		end)
	end)
end)

-- playerremoved: cleanup events

Is the anticheat accidentally punishing non-exploiters or is it not catching walkspeed exploiters because of this incorrect calculation?

1 Like

Punishing non exploiters for walking, not even jumping.

local expectedDistancePlusLeniency = (walkSpeed + Settings.SpeedLeniency) * deltaTime

Divide it by deltaTime, not multiply.

Dimensional analysis suggests otherwise, I’m trying to get distance

(Sorry for the late replies, I posted this last night)