Hey everyone, I’m working on a third-person aiming script, but I’m running into an issue. My char isn’t looking at the mouse position correctly when aiming. I’ve tried a few things, but I’m still having trouble getting it to work as expected. Has anyone any idea on how to fix this?
wait()
local uis = game:GetService("UserInputService")
local pls = game:GetService("Players")
local rs = game:GetService("RunService")
local ts = game:GetService("TweenService")
local rep = game:GetService("ReplicatedStorage")
local wepmod = require(rep.Modules.Weapons)
local playermod = require(pls.LocalPlayer:WaitForChild("PlayerScripts"):WaitForChild("PlayerModule"))
local plr = pls.LocalPlayer
repeat
task.wait()
until plr.Character
local char = plr.Character
local cam = workspace.CurrentCamera
local curtool = nil
local isaiming = false
local aimpos = Vector3.new(7, 1, 8)
local goalpos = aimpos
local normfov = 70
local aimfov = normfov - 3
local smoothspd = 0.2
local aimoffspeed = 0.15
local normzoom = plr.CameraMinZoomDistance
local aimzoom = plr.CameraMaxZoomDistance
local curmaxzoom = aimzoom
local curminzoom = normzoom
local zoomspd = 0.1
local aimblock = false
local recoilrot = Vector3.new(0, 0, 0)
local recoilspd = 0.1
local function firstperson()
return (char.Head.Position - cam.CFrame.Position).Magnitude < 1
end
local function goodtool(tool)
if not tool then return false end
local info = wepmod.GetWeaponInfo(tool.Name)
return info ~= nil
end
local aimanim = script:FindFirstChild("AimAnimation")
local track
local function setupchar(char)
local hum = char:WaitForChild("Humanoid")
track = hum:LoadAnimation(aimanim)
local function startaim()
if not goodtool(curtool) or isaiming or aimblock then return end
if firstperson() then return end
char:WaitForChild("Info").Aiming.Value = true
aimblock = true
isaiming = true
ts:Create(cam, TweenInfo.new(0.3, Enum.EasingStyle.Sine, Enum.EasingDirection.Out), {FieldOfView = aimfov}):Play()
curmaxzoom = 3
curminzoom = 3
uis.MouseBehavior = Enum.MouseBehavior.LockCenter
playermod:ToggleShiftLock(false, true, true)
track:Play()
wait(0.3)
aimblock = false
end
local function stopaim()
if not isaiming then return end
char:WaitForChild("Info").Aiming.Value = false
isaiming = false
ts:Create(cam, TweenInfo.new(0.3, Enum.EasingStyle.Sine, Enum.EasingDirection.Out), {FieldOfView = normfov}):Play()
curmaxzoom = aimzoom
curminzoom = normzoom
uis.MouseBehavior = Enum.MouseBehavior.Default
track:Stop()
playermod:ToggleShiftLock(true, true, true)
end
uis.InputBegan:Connect(function(input, processed)
if processed then return end
if input.UserInputType == Enum.UserInputType.MouseButton2 then
startaim()
elseif input.KeyCode == Enum.KeyCode.Q then
goalpos = Vector3.new(-14, 1, 8)
elseif input.KeyCode == Enum.KeyCode.E then
goalpos = Vector3.new(6, 1, 8)
end
end)
uis.InputEnded:Connect(function(input)
if input.UserInputType == Enum.UserInputType.MouseButton2 then
stopaim()
end
end)
char.ChildAdded:Connect(function(child)
task.wait()
if child:IsA("Tool") then
curtool = child
end
end)
char.ChildRemoved:Connect(function(child)
if child == curtool then
curtool = nil
stopaim()
end
end)
rs.RenderStepped:Connect(function()
aimpos = aimpos:Lerp(goalpos, aimoffspeed)
plr.CameraMaxZoomDistance += (curmaxzoom - plr.CameraMaxZoomDistance) * zoomspd
plr.CameraMinZoomDistance += (curminzoom - plr.CameraMinZoomDistance) * zoomspd
if recoilrot.Magnitude > 0.01 then
cam.CFrame *= CFrame.Angles(math.rad(recoilrot.X), math.rad(recoilrot.Y), 0)
recoilrot = recoilrot:Lerp(Vector3.new(0, 0, 0), recoilspd)
end
if isaiming and char:FindFirstChild("Head") then
local root = hum.RootPart
local lookdir = cam.CFrame.LookVector
local rootpos = root.Position
root.CFrame = CFrame.new(rootpos.X, rootpos.Y, rootpos.Z) * CFrame.Angles(0, math.atan2(lookdir.X, lookdir.Z), 0)
local offset = cam.CFrame.RightVector * aimpos.X
local tgtpos = char.Head.Position - (lookdir * aimpos.Z) + Vector3.new(0, aimpos.Y, 0) + offset
local tgtcframe = CFrame.new(tgtpos, tgtpos + lookdir)
cam.CFrame = cam.CFrame:Lerp(tgtcframe, smoothspd)
end
end)
end
plr.CharacterAdded:Connect(setupchar)
if plr.Character then
setupchar(plr.Character)
end