Shoulder-Based Viewmodel jitters when looking horizontally

  1. What do you want to achieve?
    I want to set the CFrame of the shoulders so that they would look like a viewmodel.
    (Similar to R2DA if anyone remembers that classic)

  2. What is the issue?
    Instead of the arms being “locked” to the camera, they jitter whenever I move the camera side to side.

  3. What solutions have you tried so far?
    I tried looking for answers on the forums, different ways of setting the cframe and using heartbeat (which did fix the side ways issue, but made looking up and down jitter) and a combination of heartbeat for horizontal rotation and renderstepped for vertical rotation, but the issue persisted as it seems to be tied to which update function the cframe is being set in.

After that, you should include more details if you have any. Try to make your topic as descriptive as possible, so that it’s easier for people to help you!

function onRenderStepped()
	cameraCFrame = camera.CFrame
	local torsoX,torsoY,torsoZ = torso.CFrame:ToEulerAnglesXYZ()
	local cameraX,cameraY,cameraZ = cameraCFrame:ToEulerAnglesXYZ()
	local torsoCFrame = --* CFrame.Angles(0,torsoY,0)
	if isFirstPerson then
		local tool = character:FindFirstChildOfClass("Tool")
		if tool then
			rightShoulder.C0 = torsoCFrame:inverse() * (cameraCFrame * CFrame.Angles(0,math.rad(90),0) *,-1,1))
			leftShoulder.C0 = torsoCFrame:inverse() * (cameraCFrame * CFrame.Angles(0,math.rad(-90),0) *,-1,1))
			rightShoulder.C0 =, 0.5, 0) * CFrame.Angles(0, math.pi/2, 0)
			leftShoulder.C0 =, 0.5, 0) * CFrame.Angles(0, -math.pi/2, 0)

Thank you for reading and at least considering helping!

Alright! After a bit of experimentation, I found a solution!
Basically instead of using torso.CFrame, you only use the torso’s position and use the camera’s rotation.

local torsoCFrame = CFrame.lookAt(torso.Position,torso.Position+cameraCFrame.LookVector*,0,1))

Not sure if it’s the best solution, but it worked for me!
Although it’s not completely what I wanted, as the viewmodel does change with torso’s rotation.

Alright, I have done it exactly how I wanted it to be!
To achieve the effect I wanted (the viewmodel being fully locked to the camera) I had to first create a CFrame using the HumanoidRootPart’s position and the camera’s look vector for the original CFrame.
Then we get the offset between the Torso and HumanoidRootPart and apply the offset to the CFrame we’re gonna use. And now we get exactly the CFrame we want without any jittering!

And now to explain it simply:

  1. Get the offset between HumanoidRootPart and Torso
  2. Use the HumanoidRootPart and CameraCFrame.LookVector to get a good looking effect.
  3. Apply the offset to gotten CFrame!

Here’s how the code snippet would look like:

local torsoOffsetCFrame = humanoidRootPart.CFrame:toObjectSpace(torso.CFrame)
local torsoCFrame = CFrame.lookAt(humanoidRootPart.Position,humanoidRootPart.Position+cameraCFrame.LookVector*,0,1))*torsoOffsetCFrame

I hope this helps anyone who has the same issue as me! <3

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