local function a()local a=PlayersService.LocalPlayer if a and(game.Workspace.CurrentCamera and game.Workspace.CurrentCamera.CameraType==Enum.CameraType.Custom)then return true end return false end local function Z()if EnabledCamera then EnabledCamera:Update()end if EnabledOcclusion and not VRService.VREnabled then EnabledOcclusion:Update(EnabledCamera)end if shouldUsePlayerScriptsCamera()then TransparencyController:Update()end end local function T(a)if EnabledCamera~=a then if EnabledCamera then EnabledCamera:SetEnabled(false)end EnabledCamera=a if EnabledCamera then EnabledCamera:SetEnabled(true)end end end local function D(Z)if Z==Enum.DevComputerMovementMode.ClickToMove.Name then if FFlagUserNoCameraClickToMove then return end ClickToMove:Start()T(nil)TransparencyController:SetEnabled(true)else local a=workspace.CurrentCamera and workspace.CurrentCamera.CameraType if VRService.VREnabled and a~=Enum.CameraType.Scriptable then T(VRCamera)TransparencyController:SetEnabled(false)elseif(a==Enum.CameraType.Custom or not AllCamerasInLua)and Z==Enum.ComputerCameraMovementMode.Classic.Name then T(ClassicCamera)TransparencyController:SetEnabled(true)elseif(a==Enum.CameraType.Custom or not AllCamerasInLua)and Z==Enum.ComputerCameraMovementMode.Follow.Name then T(FollowCamera)TransparencyController:SetEnabled(true)elseif(a==Enum.CameraType.Custom or not AllCamerasInLua)and(isOrbitalCameraEnabled and Z==Enum.ComputerCameraMovementMode.Orbital.Name)then T(OrbitalCamera)TransparencyController:SetEnabled(true)elseif AllCamerasInLua and CameraTypeEnumMap[a]then T(CameraTypeEnumMap[a])TransparencyController:SetEnabled(false)else T(nil)TransparencyController:SetEnabled(false)end ClickToMove:Stop()end local D=a()local U=getCameraOcclusionMode()if EnabledOcclusion==Invisicam and(U~=Enum.DevCameraOcclusionMode.Invisicam or not D)then Invisicam:Cleanup()end if D then if U==Enum.DevCameraOcclusionMode.Zoom and(isOrbitalCameraEnabled and Z~=Enum.ComputerCameraMovementMode.Orbital.Name)then EnabledOcclusion=PopperCam elseif U==Enum.DevCameraOcclusionMode.Invisicam then EnabledOcclusion=Invisicam else EnabledOcclusion=nil end else EnabledOcclusion=nil end end local function U(a)if a==Enum.CameraType.Scriptable then if UserInputService.MouseBehavior==Enum.MouseBehavior.LockCenter then UserInputService.MouseBehavior=Enum.MouseBehavior.Default end end end local function L(a)TransparencyController:SetSubject(a)end local function h()D(getCurrentCameraMode())local a=workspace.CurrentCamera if a then if cameraSubjectChangedConn then cameraSubjectChangedConn:disconnect()end if cameraTypeChangedConn then cameraTypeChangedConn:disconnect()end cameraSubjectChangedConn=(a:GetPropertyChangedSignal("\067\097\109\101\114\097\083\117\098\106\101\099\116")):connect(function()L(a.CameraSubject)end)cameraTypeChangedConn=(a:GetPropertyChangedSignal("\067\097\109\101\114\097\084\121\112\101")):connect(function()D(getCurrentCameraMode())U(a.CameraType)end)L(a.CameraSubject)U(a.CameraType)end end local function g(a)workspace.Changed:connect(function(a)if a=="\067\117\114\114\101\110\116\067\097\109\101\114\097"then h()end end)a.Changed:connect(function(a)D(getCurrentCameraMode())end)GameSettings.Changed:connect(function(a)D(getCurrentCameraMode())end)RunService:BindToRenderStep("\099\097\109\101\114\097\082\101\110\100\101\114\085\112\100\097\116\101",Enum.RenderPriority.Camera.Value,Z)h()D(getCurrentCameraMode())end do while PlayersService.LocalPlayer==nil do PlayersService.PlayerAdded:wait()end hasLastInput=pcall(function()lastInputType=UserInputService:GetLastInputType()UserInputService.LastInputTypeChanged:connect(function(a)lastInputType=a end)end)g(PlayersService.LocalPlayer)end local function V()D(getCurrentCameraMode())end;(VRService:GetPropertyChangedSignal("\086\082\069\110\097\098\108\101\100")):connect(V)

local function shouldUseOcclusionModule()
	local player = PlayersService.LocalPlayer
	if player and game.Workspace.CurrentCamera and game.Workspace.CurrentCamera.CameraType == Enum.CameraType.Custom then
		return true
	end
	return false
end

local function Update()
	if EnabledCamera then
		EnabledCamera:Update()
	end
	if EnabledOcclusion and not VRService.VREnabled then
		EnabledOcclusion:Update(EnabledCamera)
	end
	if shouldUsePlayerScriptsCamera() then
		TransparencyController:Update()
	end
end

local function SetEnabledCamera(newCamera)
	if EnabledCamera ~= newCamera then
		if EnabledCamera then
			EnabledCamera:SetEnabled(false)
		end
		EnabledCamera = newCamera
		if EnabledCamera then
			EnabledCamera:SetEnabled(true)
		end
	end
end

local function OnCameraMovementModeChange(newCameraMode)
	if newCameraMode == Enum.DevComputerMovementMode.ClickToMove.Name then
		if FFlagUserNoCameraClickToMove then
			--No longer responding to ClickToMove here!
			return
		end
		ClickToMove:Start()
		SetEnabledCamera(nil)
		TransparencyController:SetEnabled(true)
	else
		local currentCameraType = workspace.CurrentCamera and workspace.CurrentCamera.CameraType
		if VRService.VREnabled and currentCameraType ~= Enum.CameraType.Scriptable then
			SetEnabledCamera(VRCamera)
			TransparencyController:SetEnabled(false)		
		elseif (currentCameraType == Enum.CameraType.Custom or not AllCamerasInLua) and newCameraMode == Enum.ComputerCameraMovementMode.Classic.Name then
			SetEnabledCamera(ClassicCamera)			
			TransparencyController:SetEnabled(true)
		elseif (currentCameraType == Enum.CameraType.Custom or not AllCamerasInLua) and newCameraMode == Enum.ComputerCameraMovementMode.Follow.Name then
			SetEnabledCamera(FollowCamera)
			TransparencyController:SetEnabled(true)
		elseif (currentCameraType == Enum.CameraType.Custom or not AllCamerasInLua) and (isOrbitalCameraEnabled and (newCameraMode == Enum.ComputerCameraMovementMode.Orbital.Name)) then
			SetEnabledCamera(OrbitalCamera)
			TransparencyController:SetEnabled(true)
		elseif AllCamerasInLua and CameraTypeEnumMap[currentCameraType] then
			SetEnabledCamera(CameraTypeEnumMap[currentCameraType])
			TransparencyController:SetEnabled(false)
		else -- Our camera movement code was disabled by the developer
			SetEnabledCamera(nil)
			TransparencyController:SetEnabled(false)
		end
		ClickToMove:Stop()
	end
	
	local useOcclusion = shouldUseOcclusionModule()
	local newOcclusionMode = getCameraOcclusionMode()
	if EnabledOcclusion == Invisicam and (newOcclusionMode ~= Enum.DevCameraOcclusionMode.Invisicam or (not useOcclusion)) then
		Invisicam:Cleanup()
	end
	
	-- PopperCam does not work with OrbitalCamera, as OrbitalCamera's distance can be fixed.
	if useOcclusion then	
		if newOcclusionMode == Enum.DevCameraOcclusionMode.Zoom and ( isOrbitalCameraEnabled and newCameraMode ~= Enum.ComputerCameraMovementMode.Orbital.Name ) then
			EnabledOcclusion = PopperCam
		elseif newOcclusionMode == Enum.DevCameraOcclusionMode.Invisicam then
			EnabledOcclusion = Invisicam
		else
			EnabledOcclusion = nil
		end
	else
		EnabledOcclusion = nil
	end
end

local function OnCameraTypeChanged(newCameraType)
	if newCameraType == Enum.CameraType.Scriptable then
		if UserInputService.MouseBehavior == Enum.MouseBehavior.LockCenter then
			UserInputService.MouseBehavior = Enum.MouseBehavior.Default
		end
	end
end


local function OnCameraSubjectChanged(newSubject)
	TransparencyController:SetSubject(newSubject)
end

local function OnNewCamera()
	OnCameraMovementModeChange(getCurrentCameraMode())

	local currentCamera = workspace.CurrentCamera
	if currentCamera then
		if cameraSubjectChangedConn then
			cameraSubjectChangedConn:disconnect()
  		end

		if cameraTypeChangedConn then
			cameraTypeChangedConn:disconnect()
		end

		cameraSubjectChangedConn = currentCamera:GetPropertyChangedSignal("CameraSubject"):connect(function()
			OnCameraSubjectChanged(currentCamera.CameraSubject)
		end)
	
		cameraTypeChangedConn = currentCamera:GetPropertyChangedSignal("CameraType"):connect(function()
			OnCameraMovementModeChange(getCurrentCameraMode())
			OnCameraTypeChanged(currentCamera.CameraType)
  		end)

		OnCameraSubjectChanged(currentCamera.CameraSubject)
		OnCameraTypeChanged(currentCamera.CameraType)
	end
end


local function OnPlayerAdded(player)
	workspace.Changed:connect(function(prop)
		if prop == 'CurrentCamera' then
			OnNewCamera()
		end
	end)

	player.Changed:connect(function(prop)
		OnCameraMovementModeChange(getCurrentCameraMode())
	end)

	GameSettings.Changed:connect(function(prop)
		OnCameraMovementModeChange(getCurrentCameraMode())
	end)

	RunService:BindToRenderStep("cameraRenderUpdate", Enum.RenderPriority.Camera.Value, Update)

	OnNewCamera()
	OnCameraMovementModeChange(getCurrentCameraMode())
end

do
	while PlayersService.LocalPlayer == nil do PlayersService.PlayerAdded:wait() end
	hasLastInput = pcall(function()
		lastInputType = UserInputService:GetLastInputType()
		UserInputService.LastInputTypeChanged:connect(function(newLastInputType) 
			lastInputType = newLastInputType
		end)
	end)
	OnPlayerAdded(PlayersService.LocalPlayer)
end

local function OnVREnabled()
	OnCameraMovementModeChange(getCurrentCameraMode())
end

VRService:GetPropertyChangedSignal("VREnabled"):connect(OnVREnabled)
