First-person camera fighting for control in scripted sequence

I recently gained some inspiration when I saw a video on Hello Neighbor 2, Alpha 1. Specifically, this scene:

https://youtu.be/pPHm3dirrVE?t=364

(timestamp is 6:15 if the video doesn’t start at the correct time)

However, I ran into a problem with Roblox’s first-person camera

What it looks like when you’re caught in first-person:

What it’s supposed to look like (caught in third-person):

The code:

local ReplicatedStorage = game:GetService("ReplicatedStorage")
local RunService = game:GetService("RunService")

local Camera = workspace.CurrentCamera

local Player = game:GetService("Players").LocalPlayer

ReplicatedStorage.Remotes.DoCatch.OnClientEvent:Connect(function()
	local Character = Player.Character
	
	local NPC = workspace.NPC
	
	local Connection1
	local Connection2
	
	Character.Animate.Disabled = true
	
	Camera.CameraType = Enum.CameraType.Scriptable
	Camera.CameraSubject = nil
	
	for _, Object in pairs(Character:GetDescendants()) do
		if Object:IsA("BasePart") and Object ~= Character.PrimaryPart then
			Object.Transparency = 0
		end
	end
	
	local PlayerDrag = Character.Humanoid.Animator:LoadAnimation(ReplicatedStorage.Drag.DragPlayer)
	
	for _, Animation in pairs(Character.Humanoid.Animator:GetPlayingAnimationTracks()) do
		Animation:Stop()
	end
	
	PlayerDrag.Looped = true
	PlayerDrag:Play()
	
	Connection1 = RunService.RenderStepped:Connect(function()
		for _, Object in pairs(Character:GetDescendants()) do
			if Object:IsA("BasePart") and Object ~= Character.PrimaryPart then
				Object.Transparency = 0
			end
		end
		
		Camera.CFrame = Character.Head.CFrame
		
		Character:PivotTo(NPC:GetPivot() * CFrame.Angles(0, math.rad(180), 0) * CFrame.new(0, 0, -3))
	end)
	
	Connection2 = ReplicatedStorage.Remotes.DoCatchEnded.OnClientEvent:Connect(function()
		Connection1:Disconnect()
		Connection2:Disconnect()
		
		Character.Animate.Disabled = false
		
		PlayerDrag:Stop()
		
		Camera.CameraType = Enum.CameraType.Custom
		Camera.CameraSubject = Character.Humanoid
	end)
end)

The DoCatch remote is fired when the NPC touches the player, and DoCatchEnded is fired when the sequence ends.

1 Like