Cutscene re playing Mid cutscene

Im working on a game and the cutscene just plays again mid cutscene that makes you in a unlimited loop

İ tried adding debounce but it didnt work
Heres a video
its so laggy idk why
robloxapp-20230316-2136186.wmv (1.7 MB)

sorry if the video is laggy idk whats wrong with my pc i
Theres 1 script that is important its the starter player script “local”

game.Workspace.Cutscenes.CutSc.Touched:Connect(function(hit)
	-- Services
	local ReplicatedStorage = game:GetService("ReplicatedStorage")
	local RunService = game:GetService("RunService")

	local CodesOtaku = ReplicatedStorage:WaitForChild("CodesOtaku")
	local CutsceneModule = CodesOtaku:WaitForChild("CutsceneModule")

	repeat wait() until workspace.CurrentCamera -- Wait until camera is found
	-- Constructor

	local Camera = workspace.CurrentCamera
	local Looping = false
	local Speed = 1
	local FreezeControls = false

	-- Loading
	local CutsceneFolder = workspace.Cutscenes:WaitForChild("NewCutsceneSeek") -- The folder that contains the cutscene data (Cameras...)
	local Destroy = true -- Destroy folder after loading? you don't want your player to see your cameras floating around!
	local NoYield = false -- Generally you want this to be set to false, because loading takes a little bit of time, and you don't want to interact with the cutscene when it's not loaded
	local SafeMode = true -- This is adviced to be turned on, especially if the cutscene folder data is too big to load at one frame. when turned on, it loads a camera every frame, not all at once.

	local Cutscene = require(CutsceneModule)

	local Demo = Cutscene.new(Camera, Looping, Speed, FreezeControls) -- Create cutscene
	Demo:Load(CutsceneFolder, Destroy, NoYield, SafeMode) -- Load cutscene data from folder

	local PlayOnPartTouch = script:FindFirstChild("PlayOnPartTouch")
	local PlayOnPlayerJoin = script:FindFirstChild("PlayOnPlayerJoin")
	local PlayOnCharacterAdded = script:FindFirstChild("PlayOnCharacterAdded")
	local PlayOnCharacterDied = script:FindFirstChild("PlayOnCharacterDied")
	local PlayOnEventFire = script:FindFirstChild("PlayOnEventFire")
	local PlayOnRemoteEventFire = script:FindFirstChild("PlayOnRemoteEventFire")
	local ProtectTheCharacterWhilePlaying = script:FindFirstChild("ProtectTheCharacterWhilePlaying")
	local CharacterProtector = script:FindFirstChild("CharacterProtector")
	local Music = script:FindFirstChild("Music")
	local StopMusicWhenFinished = script:FindFirstChild("StopMusicWhenFinished")
	local StopOnEventFire = script:FindFirstChild("StopOnEventFire")
	local StopOnRemoteEventFire = script:FindFirstChild("StopOnRemoteEventFire")
	local PlayOnce = script:FindFirstChild("PlayOnce")
	local Debounce = script:FindFirstChild("Cooldown")
	local OnFinishedRemove = script:FindFirstChild("OnFinishedRemove")
	local bin = true
	local Player = game:GetService("Players").LocalPlayer
	local CutsceneGui = script:FindFirstChild("Cutscene")

	-- Cutscene duration in seconds
	local duration = Demo:GetDuration()
	-- Check the module script for more functions and then do like this "Demo:FunctionName()" like the above example of duration

	-- a better alternative implementation for the wait function
	function wait_time(duration)
		local start = tick()
		local Heartbeat = game:GetService("RunService").Heartbeat
		repeat Heartbeat:Wait() until (tick() - start) >= duration
		return (tick() - start)
	end

	-- Support for debounce
	function PlayCutscene()
		if bin then
			bin = false
			Music:Play()
			if ProtectTheCharacterWhilePlaying and ProtectTheCharacterWhilePlaying.Value and Player.Character then
				CharacterProtector.Parent = Player.Character
			end
			Demo:Play()
		end
	end

	Demo.EStop.Event:Connect(function()
		wait_time(Debounce.Value)
		CharacterProtector.Parent = nil
		if PlayOnce then
			if not PlayOnce.Value then
				bin = true
			end
		else
			bin = true
		end
		if StopMusicWhenFinished and StopMusicWhenFinished.Value then
			Music:Stop()
			if OnFinishedRemove then
				for i,v in pairs(OnFinishedRemove:GetChildren()) do
					if v:IsA("ObjectValue") then
						if v.Value then
							v.Value:Destroy()
						end
					end
				end
			end
		end
	end)

	-- Update the cutscene every render frame
	RunService.RenderStepped:Connect(function(Delta)
		Demo:Update(Delta)
	end)

	if PlayOnPlayerJoin and PlayOnPlayerJoin.Value then
		-- Play the cutscene
		PlayCutscene()
	end

	if PlayOnPartTouch then
		local part = script.PlayOnPartTouch.Value
		if part and part:IsA("BasePart") then
			part.Touched:Connect(function(hit)
				if hit.Parent == Player.Character then
					PlayCutscene()
				end
			end)
		end
		PlayOnPartTouch:Destroy()
	end

	if PlayOnEventFire then
		local e = PlayOnEventFire.Value
		if e and e:IsA("BindableEvent") then
			e.Event:Connect(PlayCutscene)
		end
		PlayOnEventFire:Destroy()
	end

	if PlayOnRemoteEventFire then
		local e = PlayOnRemoteEventFire.Value
		if e and e:IsA("RemoteEvent") then
			e.OnClientEvent:Connect(PlayCutscene)
		end
		PlayOnRemoteEventFire:Destroy()
	end

	if StopOnRemoteEventFire then
		local e = StopOnRemoteEventFire.Value
		if e and e:IsA("RemoteEvent") then
			e.OnClientEvent:Connect(function()
				Demo:Stop()
			end)
		end
		StopOnRemoteEventFire:Destroy()
	end

	if StopOnRemoteEventFire then
		local e = StopOnRemoteEventFire.Value
		if e and e:IsA("RemoteEvent") then
			e.OnClientEvent:Connect(function()
				Demo:Stop()
			end)
		end
		StopOnRemoteEventFire:Destroy()
	end

	if CutsceneGui then
		CutsceneGui.Parent = Player:WaitForChild("PlayerGui")
		local SkipCutsceneButton = CutsceneGui:FindFirstChild("SkipCutscene", true)
		local PlayCutsceneButton = CutsceneGui:FindFirstChild("PlayCutscene", true)

		if SkipCutsceneButton and SkipCutsceneButton:IsA("GuiButton") then
			SkipCutsceneButton.MouseButton1Click:Connect(function()
				Demo:Stop()
			end)
		end

		if PlayCutsceneButton and PlayCutsceneButton:IsA("GuiButton") then
			PlayCutsceneButton.MouseButton1Click:Connect(function()
				PlayCutscene()
			end)
		end
		Demo.EStop.Event:Connect(function()
			CutsceneGui.Enabled = false
		end)
	end

	local Character = Player.Character or Player.CharacterAdded:Wait()

	if PlayOnCharacterAdded and PlayOnCharacterAdded.Value then
		PlayCutscene()
	end
	if PlayOnCharacterDied and PlayOnCharacterDied.Value then
		local Humanoid = Character:WaitForChild("Humanoid")
		Character:WaitForChild("Humanoid").Died:Connect(function()
			PlayCutscene()
		end)
	end
	PlayOnCharacterAdded:Destroy()
end)
1 Like

Your video is an audio file, I can’t watch it. Also it might be because you’re using RenderStepped. Try using :BindToRenderStep() and :UnbindFromRenderStep() instead.

Or the problem could be your hit part, as it runs indefinitely everytime your character touches it. In this case you can try using a bool value like isHit.
Example:

--Code
local isHit = false
--Code
part.Touched:Connect(function(hit)
     if hit.Parent == Player.Character and not isHit then
                     isHit = true
		     PlayCutscene()
	      end
      end)

Currently very tired and replying at 3am so I may have skimmed through the code. I apologise if I misunderstood anything and/or didn’t help. Also code formatting’s a little wack since I’m on mobile.

İts not an audio file its an downloadable video file from roblox itself

Oh my bad, it seems that i somehow managed to download something completely irrelevant…? I’ll take a look again.

Edit: I can’t tell if it’s a video issue or a mobile issue, but the video is really laggy and I can barely make out anything. The most I got out of it was a cutscene of a monster emerging before (I presume this is the problem?) it immediately plays a cutscene of going back to the player.

Yea its pretty laggy because of roblox studio issue the problem is when i trigger the cutscene it goes to the monster then goes back to the player then go back to the monsters spawn place until the player gets killed

Sorry for the late reply, went to sleep since it was getting really late.

I’m gonna assume that your whole mass of variables are Bool Values under the script?

local PlayOnPartTouch = script:FindFirstChild("PlayOnPartTouch")
local PlayOnPlayerJoin = script:FindFirstChild("PlayOnPlayerJoin")
local PlayOnCharacterAdded = script:FindFirstChild("PlayOnCharacterAdded")
local PlayOnCharacterDied = script:FindFirstChild("PlayOnCharacterDied")

Also a little confused when reading this line (Which I’m gonna assume is to press ‘E’ to stop the cutscene):

Demo.EStop.Event:Connect(function()
		wait_time(Debounce.Value)
		CharacterProtector.Parent = nil
		if PlayOnce then
			if not PlayOnce.Value then
				bin = true
			end
		else

This basically checks if the PlayOnce value is true, then checks again if it’s false (which won’t happen because PlayOnce is obviously already true). I’m not sure if this is a mistake or if this is intentional in case PlayOnce happens to become false after the check.

I still think the RenderStepped event is the cause of your problems since it updates the Cutscene on every frame regardless of which code is running, including your :Stop() command.

Maybe instead of using:

RunService.RenderStepped:Connect(function(Delta)
		Demo:Update(Delta)
	end)

Try adding this line of code for each time you play a cutscene:

Local function update(Delta)
   Demo:Update(Delta)
end

if PlayOnPlayerJoin and PlayOnPlayerJoin.Value then
		-- Play the cutscene
		PlayCutscene()
        RunService:BindToRenderStep("Update", 1, update)
	end

Parameters → (“Name of bind”, Priority, function to bind)

So when you’re using Demo:Stop(), you should add this line of code:

if StopOnRemoteEventFire then
	local e = StopOnRemoteEventFire.Value
	if e and e:IsA("RemoteEvent") then
		e.OnClientEvent:Connect(function()
			Demo:Stop()
			RunService:UnbindFromRenderStep("Update")
		end)
	end
	StopOnRemoteEventFire:Destroy()
end

This is all under the assumption that this script uses only one cutscene.

Sorry for the late reply but it didnt work also there is 7 cutscene cameras