Making drone (vector force) go slower

My FPV drone system will be used in a pvp game to hit players and explode. But the drone is flying too fast to hit anything than terrain. How would I go about making it slower?

Watch 2025-07-06 19-20-41 | Streamable (Take a look at the end of the video - that’s when it’s at its worst.)

I’ve tried messing around with the gainforce and loseforce, but that doesn’t help.
Client controller script (network ownership given to player on server)

-- // Services
local UIS = game:GetService("UserInputService")
local RS = game:GetService("RunService")

-- // Idents
local plr = game.Players.LocalPlayer
local cam = workspace.CurrentCamera

-- // Code
local controlFPVdrone = {}

function controlFPVdrone.initializeControls(droneModel : Model)
	local cache = {}
	
	-- Players' Character
	local hum : Humanoid = plr.Character.Humanoid
	hum.WalkSpeed = 0
	
	-- Identifying
	local droneModelMain : Part = droneModel:WaitForChild("Main")
	local cameraPoint : Part = droneModel.CamPart
	
	local droneMass = droneModelMain:GetMass()
	
	local hoverForce = (droneMass * workspace.Gravity) -- hover
	local gainForce = (hoverForce * 1.15) -- go up
	local loseForce = (hoverForce * 0.85) -- go down
	
	-- Instancing
	local vectorForce = Instance.new("VectorForce", droneModelMain)
	local alignOrientationForce = Instance.new("AlignOrientation", droneModelMain)
	local forceAttachment = Instance.new("Attachment", droneModelMain)
	
	-- Main Logic
	vectorForce.ApplyAtCenterOfMass = true
	vectorForce.RelativeTo = Enum.ActuatorRelativeTo.Attachment0
	vectorForce.Attachment0 = forceAttachment
	
	vectorForce.Force = forceAttachment.WorldCFrame.UpVector * hoverForce
	
	alignOrientationForce.Attachment0 = forceAttachment
	alignOrientationForce.RigidityEnabled = false
	alignOrientationForce.Responsiveness = 50
	alignOrientationForce.MaxTorque = math.huge
	alignOrientationForce.Mode = Enum.OrientationAlignmentMode.OneAttachment
	alignOrientationForce.CFrame = CFrame.new() * CFrame.Angles(math.rad(droneModelMain.Orientation.X),math.rad(droneModelMain.Orientation.Y),math.rad(droneModelMain.Orientation.Z))
	
	-- Placing Camera
	plr.ReplicationFocus = droneModelMain
	cam.CameraType = Enum.CameraType.Scriptable
	cam.CFrame = cameraPoint.CFrame
	UIS.MouseBehavior = Enum.MouseBehavior.LockCenter
	
	-- Controlling
	local inpBeganCon = UIS.InputBegan:Connect(function(input, registered)
		if input.UserInputType == Enum.UserInputType.MouseButton1 then
			vectorForce.Force = forceAttachment.WorldCFrame.UpVector * gainForce
		end
		
		if input.UserInputType == Enum.UserInputType.MouseButton2 then
			vectorForce.Force = forceAttachment.WorldCFrame.UpVector * loseForce
		end
	end)
	local inpEndCon = UIS.InputEnded:Connect(function(input, registered)
		if input.UserInputType == Enum.UserInputType.MouseButton1 or input.UserInputType == Enum.UserInputType.MouseButton2 then
			vectorForce.Force = forceAttachment.WorldCFrame.UpVector * hoverForce
		end
	end)
	
	local rSteppedCon = RS.RenderStepped:Connect(function(dt)
		-- camera updating
		cam.CFrame = cameraPoint.CFrame
		
		-- tilting
		local mouseDelta = UIS:GetMouseDelta() / 10
		local mdY = -mouseDelta.Y
		local mdX = -mouseDelta.X
		
		-- rotating
		local yRot = 0
		if UIS:IsKeyDown(Enum.KeyCode.A) then
			yRot += 0.01
		elseif UIS:IsKeyDown(Enum.KeyCode.D) then
			yRot -= 0.01
		end
		
		-- final align orientation positioning
		alignOrientationForce.CFrame = alignOrientationForce.CFrame * CFrame.Angles(math.rad(mdX),yRot,math.rad(mdY))
	end)
	
	-- Caching
	table.insert(cache, inpBeganCon)
	table.insert(cache, inpEndCon)
	
	return cache
end

return controlFPVdrone

Any help is highly appreciated. Thank you.

3 Likes

I believe this behavior is being caused by that fact that the force is not being damped. Vector3 forces constantly apply a force to the object. So even when you apply loseForce, the velocity is still increasing.

In order to combat this you would need to apply a damping force. For example, you could get the models velocity and then multiply it by -0.1. Then apply that force to the model. Or, when you click mouseButton2, you could apply a force of -loseForce.

Ex.

--put somewhere at top of function controlFPVdrone.initializeControls
local droneVelocity = droneModelMain.AssemblyLinearVelocity

--replace mouseButton2 code
if input.UserInputType == Enum.UserInputType.MouseButton2 then
	vectorForce.Force = forceAttachment.WorldCFrame.UpVector * loseForce * -SOME_MULTIPLIER
end

--replace hover code
if input.UserInputType == Enum.UserInputType.MouseButton1 or input.UserInputType == Enum.UserInputType.MouseButton2 then
			vectorForce.Force = (forceAttachment.WorldCFrame.UpVector * hoverForce) + (-droneVelocity * SOME_OTHER_MULTIPLIER)
end

You could also experimenting with using a LinearVelocity constraint instead, since the Roblox document states that they are better for forces applied over time.

1 Like

Thank you for the tip! I saw that I forgot creating drag, so I made that and thanks for the drag “recepie” What made the biggest change was making a speed capper. Works like butter now :slight_smile: Watch 2025-07-07 18-29-45 | Streamable

        -- cap speed
		local maxSpeed = 50
		local currentMainpartVelocity = droneModelMain.AssemblyLinearVelocity
		local currentMainpartSpeed = currentMainpartVelocity.Magnitude
		
		if currentMainpartSpeed > maxSpeed then
			droneModelMain.AssemblyLinearVelocity = currentMainpartVelocity.Unit * maxSpeed
		end
2 Likes

This topic was automatically closed 14 days after the last reply. New replies are no longer allowed.