Question about setting camera CFrame angle

local function Fire()
	local OriginalCFrame = Camera.CFrame
	Camera.CFrame = Camera.CFrame * CFrame.Angles(math.rad(5),0,0)
	
	local tweenInfo = TweenInfo.new(0.2)
	local goal = {CFrame = OriginalCFrame}
	
	local RecoilRecover = TweenService:Create(Camera, tweenInfo, goal)
	
	RecoilRecover:Play()
end

So I’m trying to simulate gun recoil yeah?
Pretty standard stuff, when the user presses mousebutton1 down, the fire function is called and the initial camera jolt upwards is tweened back to the OriginalCFrame.
However, one thing to note is that OriginalCFrame saves not only the camera’s original angle but also its previous position.
So when the player walks and fires, it gets all buggy and they can see their viewmodel for a split second.

TL;DR
Is there a way to set only the camera’s CFrame orientation and exclude the position?

use the Camera.CFrame.Rotation

Yeah, I know CFrame.Rotation exists, but use it how?

Use this

local function Fire()
	local OriginalCFrame = Camera.CFrame.Rotation 
	Camera.CFrame = Camera.CFrame * CFrame.Angles(math.rad(5),0,0)
	
	local tweenInfo = TweenInfo.new(0.2)
	local goal = {CFrame = Camera.CFrame * OriginalCFrame}
	
	local RecoilRecover = TweenService:Create(Camera, tweenInfo, goal)
	
	RecoilRecover:Play()
end

So uh, none of the suggestions has worked so far, it’d be nice if I can solve this problem today.
also bump

If the previous position is the issue, wouldn’t the solution be changing the position to where you want it to be?

I haven’t tested the code in the original post, but these might help in the meantime:

https://developer.roblox.com/en-us/api-reference/datatype/CFrame

I tested it and I think I understand the issue, check this post out along with other posts in the topic:

I got the same issue of the camera position stuttering when moving and shooting at the same time:

local Camera = game.Workspace.CurrentCamera
local TweenService = game:GetService("TweenService")
local userInputService = game:GetService("UserInputService")

local function Fire()
	Camera.CFrame = Camera.CFrame * CFrame.Angles(math.rad(5),0,0)

	local tweenInfo = TweenInfo.new(0.2)
	local goal = {CFrame = Camera.CFrame * CFrame.Angles(math.rad(-5),0,0)}

	local RecoilRecover = TweenService:Create(Camera, tweenInfo, goal)

	RecoilRecover:Play()
end

userInputService.InputBegan:Connect(function(input)
	if input.UserInputType == Enum.UserInputType.MouseButton1 then
		print("The left mouse button has been pressed!")
		Fire()
	end
end)

Anyways, TweenService isn’t great in this case it seems. Lerping or using RunService might work or the stuff other people said in other topics.

Same results as my original post.
https://gyazo.com/845dd2f749b473a2993051231a2af727

However, I would have to account for fps unlockers if I’m using these methods, which I’m too lazy to do.

1 Like

I’m also trying some alternative methods such as:

local function Fire()
	Camera.CFrame = Camera.CFrame * CFrame.Angles(math.rad(5),0,0)
	
	local current_time = 0	-- Recoil recovery using FPS independent lerp
	local LERP_TIME = 1
	while current_time < LERP_TIME do
		current_time += RunService.RenderStepped:Wait()
		Camera.CFrame = Camera.CFrame:Lerp(Camera.CFrame * CFrame.Angles(math.rad(-0.045), 0, 0),  math.min(current_time/LERP_TIME,1))
	end
end

However, the main problem with this method is I don’t understand what the maths is behind the CFrame lerp, like how would I calculate the exact unit I would need in CFrame.Angles(math.rad(-0.045), 0, 0) so that the camera returns to its original rotation?