First you gotta convert the target position into the space of the turret base, the non-rotating part. You can then find the yaw angle by doing atan2() on the X and Z components of that position. (assuming the base has its Y axis up).
I’ve actually done something like this multiple times. You would want to grab the 3D position of the mouse using mouse.Hit then also use CFrame.LookAt(BasePosition, mouse.Hit), and feed the orientation’s X-axis of the resulting CFrame to the base’s Servo, Servo as in the Actuator type usually found in Motors, Hinges, Cylindrical Constraints etc… You would want to do the same for the turret’s servo but feed the orientation’s Y-axis.
The CFrame class actually has a helper function just for this, since it’s such a common task: Roblox API CFrame:PointToObjectSpace
or you can just do the multiplication yourself like turretAttachment.WorldCFrame:Inverse() * targetPoint where the targetPoint is the world-space location as a Vector3. You generally want the target position in the coordinate space of the hinge itself, don’t use Part CFrames or you’ll have to manually account for the offsets. If you find yourself getting confused about the hinge attachments being 90-degrees off from how your brain thinks of things, you can always just add an extra reference attachment to each moving part, at the same location as the hinge pivot.
You first need to get the target point in world space, because your mouse position is a point in 2D screen space. Normally, you’d use Camera:ViewportPointToRay() to get a ray that you can use to do a raycast from the camera location into the world, and the use the RaycastResult.Position as your target point.
Once you have the target position in the space of the hinges, it’s just some basic triangle trig to work out the Euler angles you need for setting the hinge servo angles. It’s just Spherical Coordinates so you can just read the solution there on Wikipedia.
It uses the Orientation associated with the CFrame which is fed into the Servo/Hinge’s TargetAngle property, which wouldn’t bypass the AngularSpeed. Filter is just a regular part, which I set the CFrame to in order to grab the orientation from. I did this because 3 years ago I was terrible so instead I would recommend using CFrame:ToEulerAnglesXYZ(), then converting the radians to degrees using math.deg() to get the orientation instead.
assuming you havent done this already, you dont need to make it go to the server when its stuff like target angles etc, its actually better to keep it local because theres then less lag
So I used your script @ClearlyVi i copied it almost identically
--Imports
TWS=game:GetService("TweenService")
--Variables relating to the turret
local Turret= script.Parent
local Barrel= Turret.Barrel
--SETTINGS
local aggroRange=100
local bulletDamage=10
local processorTime=0.5
local Filter=Instance.new("Part")
local function aim(Positon)
local positionToAim=CFrame.lookAt(script.Parent.RotateZ.Hinge.Position,Positon)
Filter.CFrame=positionToAim
Turret.RotateY.HingeConstraint.TargetAngle=(Filter.Rotation.Y+90)
Turret.RotateZ.HingeConstraint.TargetAngle=(Filter.Orientation.X)
end
while true do
for i,v in workspace:GetChildren() do
if v:FindFirstChild("Humanoid") and (v.HumanoidRootPart.Position-Turret.Base.Middle.Position).Magnitude<100 then
aim(v.HumanoidRootPart.Position)
end
end
wait(processorTime)
end
But when I play the game the turret only has Positive angles, meaning that it does not follow the player if you are behind it