Abnormal camera stuttering when manipulating camera

Hello ! I’ve been recently writing a custom implementation for my camera, but I’ve encountered weird issues when editing character’s CFrame.

Consider the code as the following:

local cameraAPI = {}

-- Cache variables and shorthands, includes math functions as well

local CFRAME = CFrame.new
local ANGLES = CFrame.Angles

local PI = math.pi

local DEG = math.deg
local RAD = math.rad
local CLAMP = math.clamp

-- Get services

local userInputService = game:GetService("UserInputService")
local runService = game:GetService("RunService")
local players = game:GetService("Players")

-- Constants

local CAM_OFFSET = Vector3.new(0, 0.85, 1)
local Y_AXIS_LOCK = 75 -- maximum angle along Y axis

local X_SENSITIVITY = 0.015
local Y_SENSITIVITY = 0.075

-- Define misc variables

local currentCharacter
local currentCamera
local inputListener

local xAngle, yAngle = 0, 0

-- Body and functions

local function update(dt)
	local rootPart = currentCharacter.PrimaryPart
	
	local yOrientation = ANGLES(0, RAD(xAngle), 0)
	
	local displaced = rootPart.CFrame * CAM_OFFSET
	local cf = yOrientation * ANGLES(RAD(yAngle), 0, 0) + displaced

	print(rootPart.Position) -- Position doesn't give weird results, the CFrame is identic while idling

	rootPart.CFrame = yOrientation + rootPart.Position
	currentCamera.CFrame = cf
end

local function mouseMoved(input, robloxHandled)
	if input.UserInputType.Value ~= 4 or robloxHandled then return end
	
	xAngle = (xAngle - input.Delta.X * X_SENSITIVITY * PI) % 360
	yAngle = CLAMP(yAngle - input.Delta.Y * Y_SENSITIVITY * PI, -Y_AXIS_LOCK, Y_AXIS_LOCK)
end

-- Module

function cameraAPI:Init(character)
	local camera = workspace.CurrentCamera
	
	camera.CameraType = Enum.CameraType.Scriptable
	
	players.LocalPlayer.CameraMode = Enum.CameraMode.LockFirstPerson
	
	currentCamera = camera
	currentCharacter = character
	
	if inputListener and typeof(inputListener) == "RBXScriptConnection" then
		inputListener:Disconnect()
	end
	
	inputListener = userInputService.InputChanged:Connect(mouseMoved)
	
	runService:BindToRenderStep("HandleCamera", Enum.RenderPriority.Camera.Value, update)
end

function cameraAPI:Stop()
	
end

return cameraAPI

As shown in the video below, the camera starts to act unexpectedly as the character spins around for some reasons.

I think I mentioned everything, help would be appreciated !

I presume you’re trying to make a custom first person?

Yes, the issue arises when I rotate the character there rootPart.CFrame = yOrientation + rootPart.Position. I can’t seem to understand what causes this

I can provide more pictures if needed

I answered a similar problem but you can still use it. All you need to do is manipulate the origin vector and add it with an offset so it’s positioned at the head instead of the HumanoidRootPart.

EDIT: Since it’s first person, you don’t need to multiply the cframe by an offset at the end. That’s only if you want to offset it outside of the character.

1 Like

After browsing the attached topic, it still doesn’t completely solve my issue. I’ve managed to adjust it to correct the stuttery but the spinning persists :

From the post I gave on on the other thread, you can use delta again to apply it to your character’s angles.

root.CFrame *= CFrame.Angles(0, input.Delta.X / sensitivity, 0)

EDIT: Were multiplying it here instead of setting the root’s cframe as there could be instances that the player isn’t exactly upright (might have fallen down), which could lead to collision glitches.

2 Likes

Still occurring even after moving this line of code :

This certainly has to do with my current CFrame definition, the LookVector keeps changing even while idling:

Looks like I managed to solve the issue by multiplying the lookvector instead of directly doing it on the CFrame, thank you anyway !

local displaced = rootPart.CFrame.LookVector * CAM_OFFSET
1 Like