 # Limiting rotation for a turret

Hello. I am making a turret that points at the player’s mouse, and I tried to limit the rotation on the Y-axis but doesn’t seem to work properly. Here is a video:

And here is my code:

``````RunService.Heartbeat:Connect(function(dt)
local toAim = mouse.Hit.Position;
local CF = CFrame.lookAt(turret.Position, Vector3.new(toAim.X, turret.Position.Y, toAim.Z));
local X, Y, Z = CF:ToOrientation();
Y = math.clamp(Y, -2, 2)
turret.CFrame = CFrame.new(turret.Position)*CFrame.Angles(0, Y, 0)
end)
``````

Thank you so much for reading! Any help is appreciated.

Is the angle supposed to be between -2 degrees and 2 degrees or -2 radians and 2 radians? ToOrientation gives the angles in radians, so the limit should be in radians, too. You can use `math.rad` to convert degrees to radians.

It is supposed to be in radians.

Does this work? The 0 angle seems to be in the opposite direction than it’s supposed to.

``turret.CFrame = CFrame.new(turret.Position)*CFrame.Angles(0, math.pi+Y, 0)``
1 Like

Doesn’t seem to work as intended. Video:

Code:

``````RunService.Heartbeat:Connect(function(dt)
local toAim = mouse.Hit.Position;
local CF = CFrame.lookAt(turret.Position, Vector3.new(toAim.X, turret.Position.Y, toAim.Z));
local X, Y, Z = CF:ToOrientation();
Y = math.clamp(Y, -2, 2)
turret.CFrame = CFrame.new(turret.Position)*CFrame.Angles(0, math.pi+Y, 0)
end)
``````

Is the rotation of the character supposed to affect this?

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

local plr = Players.LocalPlayer

RunService.Heartbeat:Connect(function(dt)
local toAim = mouse.Hit.Position

local hrpCf = plr.Character.HumanoidRootPart.CFrame
local hrpDir = hrpCf.LookVector
local hrpDirX, hrpDirZ = hrpDir.X, hrpDir.Z

local targetPos = toAim.Position
local targetDirX, targetDirZ = targetPos.X-hrpCf.X, targetPos.Z-hrpCf.Z

local hrpAngle, targetAngle = math.atan2(hrpDirX, -hrpDirZ), math.atan2(targetDirX, -targetDirZ)
local y = hrpAngle+math.clamp(targetAngle-hrpAngle, -2, 2)
turret.CFrame = CFrame.new(turret.Position)*CFrame.Angles(0, y, 0)
end)``````
1 Like

Thank you so much for writing that! But, the rotation of the character isn’t supposed to affect this. I tried this too but it didn’t work. Here’s a video:

Download studio tweaks, and make sure the turret part has the face looking at the correct direction in the barrel of the turret or else things might get weird. Otherwise I believe in the original code the turret is clamped in the Global axis and not by how it was originally facing. I will take some code bits from my turret controller module to try apply it to your situation.

``````local baseCFrame = turret.CFrame -- the new XYZ axis of the turret CFrame, it's original orientation.
RunService.Heartbeat:Connect(function(dt)
local toAim = mouse.Hit.Position;
local CF = CFrame.lookAt(turret.Position, Vector3.new(toAim.X, turret.Position.Y, toAim.Z));
--math from my module
local turretRelativeCF =baseCFrame :ToObjectSpace(CF)
local _, Y , _ = turretRelativeCF:ToOrientation()
Y = math.clamp(Y, -2, 2)
local goalCFrame = baseCFrame*CFrame.fromOrientation(0,Y,0)
local rotationOnly = goalCFrame - goalCFrame.Position
turret.CFrame = CFrame.new(turret.Position)*rotationOnly
end)
``````
1 Like

It works, but the only problem now I have is that when you’re going off the limits, it’s doing some weird thing, I don’t know how to explain, but you can see it in this video: