How to use DeltaTime with Projectile

Hello,

Today I was trying to mess around with projectiles and try some hit detection. To move the projectile I decided to use RunService.Heartbeat to accomplish this. Problem is that RunService runs every single frame, which means people with different frame rates are going to get different results, as in someone with 24 FPS having the projectile moving slower than someone at 60 FPS. I have looked into it and found out I would have to use DeltaTime to make it move at the same rate no matter the FPS. When I looked at DeltaTime scripts they didn’t really work in the way I was trying to use them, moving a projectile, and I can’t really understand how to implement it in my scenario.

Example of what I would be doing:
(Server Script)

local RS = game:GetService("RunService")

RS.Heartbeat:Connect(function(deltaTime)
    --some deltaTime stuff however you would add it
    projectile.CFrame = projectile.CFrame * CFrame.new(5,0,0)
end)

Basically I do not know how I would use the DeltaTime variable to make it where the projectile moves at the same pace no matter the FPS of the user.

1 Like

Luckily this CFrame math article has the delta time math for this kind of operation.

game:GetService("RunService").Heartbeat:connect(function(dt)
	door.CFrame = door.CFrame * CFrame.Angles(0, math.rad(1)*dt*60, 0)
end)
--Math is
local rate = math.rad(1)*60 -- Not too sure about the units
local increment = rate*dt -- radians/time (or rate) * time (delta time) = radians
--unit cancellation
3 Likes

So would it be like this and the deltaTime work?

RS.Heartbeat:Connect(function(deltaTime)
    projectile.CFrame = projectile.CFrame * CFrame.new(5*deltaTime*60,0,0)
end)

yeah, theoretically it should. Practically you will need to test it with a fps unlocker or some sort.

I have been looking for an FPS limiter to test it, do you know where to find any good ones?

Searching on google, found a similar question which should work:

That’s working but do you know if there was a way I could compare them scripting wise? Not trying to eye it just to make sure.

Measure the velocity using the change in position.

local lastProjectilePosition = projectile.CFrame.Position
RS.Heartbeat:Connect(function(deltaTime)
    projectile.CFrame = projectile.CFrame * CFrame.new(5,0,0)
local currentPosition = projectile.CFrame.Position
local speed = (currentPosition - lastProjectilePosition).Magnitude/deltaTime
lastProjectilePosition = currentPosition 
end)

Thank you, I changed the 5 on CFrame to 5 * deltaTime * 60 and then tested both speeds, they were both 300 (would imagine this means they are same speed regardless of FPS).

Oh nice, looking at that number 300. This means that the rate

local rate = 5 * 60 -- = 300 speed therefore rate is 300 studs per second is the unit