My script lags a lot

I’m trying to make a slide script similar to the one in COD BO3 (one with with G Slide)
It works decently well, but for some reason the animation plays more than once causing lag

Slide Script:

local UIS = game:GetService("UserInputService")
local char = script.Parent
local slideAnim = Instance.new("Animation")
local slideAnimLeft = Instance.new("Animation")
local slideAnimRight = Instance.new("Animation")

slideAnim.AnimationId = "https://www.roblox.com/assets/?id=94674093415095"
slideAnimRight.AnimationId = "https://www.roblox.com/assets/?id=103921112029675"
slideAnimLeft.AnimationId = "https://www.roblox.com/assets/?id=90335755885310"

local Keybinds = script.Keybinds

local keybind = Enum.KeyCode.LeftControl
local canslide = true

UIS.InputBegan:Connect(function(input,gameprocessed)
	if gameprocessed then return end
		if not canslide then return end
		if input.KeyCode == keybind then
			if script.Parent.Humanoid.WalkSpeed >= 23 then
				if Keybinds.W.Value == true then
					canslide = false
					
					local playAnim = char.Humanoid:LoadAnimation(slideAnim)
					playAnim:Play()
					
					local slide = Instance.new("BodyVelocity")
					slide.MaxForce = Vector3.new(1,0,1) * 30000
					slide.Velocity = char.HumanoidRootPart.CFrame.lookVector * 100
					slide.Parent = char.HumanoidRootPart

					char.Humanoid.HipHeight = -1.5
					char.Humanoid.AutoRotate = false
					
					
					for count = 1, 8 do
						wait(.1)
						slide.Velocity *= .6
						script.Parent.Head.Running.Volume = 0
					end
					
					playAnim:Stop()
					slide:Destroy()
					
					canslide = true
					
					char.Humanoid.AutoRotate = true
					char.Humanoid.HipHeight = 0
					script.Parent.Humanoid.WalkSpeed = 16
					script.Parent.Head.Running.Volume = .5
				elseif Keybinds.S.Value == true then
					canslide = false

					local playAnim = char.Humanoid:LoadAnimation(slideAnim)
					playAnim:Play()

					local slide = Instance.new("BodyVelocity")
					slide.MaxForce = Vector3.new(1,0,1) * 30000
					slide.Velocity = char.HumanoidRootPart.CFrame.lookVector * -100
					slide.Parent = char.HumanoidRootPart

					char.Humanoid.HipHeight = -1.5
					char.Humanoid.AutoRotate = false

					for count = 1, 8 do
						wait(.1)
						slide.Velocity *= .6
						script.Parent.Head.Running.Volume = 0
					end

					playAnim:Stop()
					slide:Destroy()

					canslide = true

					char.Humanoid.AutoRotate = true
					char.Humanoid.HipHeight = 0
					script.Parent.Humanoid.WalkSpeed = 16
					script.Parent.Head.Running.Volume = .5
				elseif Keybinds.D.Value == true then
					canslide = false

					local playAnim = char.Humanoid:LoadAnimation(slideAnimRight)
					playAnim:Play()

					local slide = Instance.new("BodyVelocity")
					slide.MaxForce = Vector3.new(1,0,1) * 30000
					slide.Velocity = char.HumanoidRootPart.CFrame.RightVector * 100
					slide.Parent = char.HumanoidRootPart

					char.Humanoid.HipHeight = -1.5
					char.Humanoid.AutoRotate = false

					for count = 1, 8 do
						wait(.1)
						slide.Velocity *= .6
						script.Parent.Head.Running.Volume = 0
					end

					playAnim:Stop()
					slide:Destroy()

					canslide = true

					char.Humanoid.AutoRotate = true
					char.Humanoid.HipHeight = 0
					script.Parent.Humanoid.WalkSpeed = 16
					script.Parent.Head.Running.Volume = .5
				elseif Keybinds.A.Value == true then
					canslide = false

					local playAnim = char.Humanoid:LoadAnimation(slideAnimLeft)
					playAnim:Play()

					local slide = Instance.new("BodyVelocity")
					slide.MaxForce = Vector3.new(1,0,1) * 30000
					slide.Velocity = char.HumanoidRootPart.CFrame.RightVector * -100
					slide.Parent = char.HumanoidRootPart

					char.Humanoid.HipHeight = -1.5
					char.Humanoid.AutoRotate = false
					
					for count = 1, 8 do
						wait(.1)
						slide.Velocity *= .6
						script.Parent.Head.Running.Volume = 0
					end

					playAnim:Stop()
					slide:Destroy()

					canslide = true

					char.Humanoid.AutoRotate = true
					char.Humanoid.HipHeight = 0
					script.Parent.Humanoid.WalkSpeed = 16
					script.Parent.Head.Running.Volume = .5
				end
			end
	end
end)

G Slide Script:

local char = script.Parent.Parent
local slideg = Instance.new("Animation")
local slideAnimLeft = Instance.new("Animation")
local slideAnimRight = Instance.new("Animation")

local Keybinds = script.Parent.Keybinds
local uis = game:GetService("UserInputService")

slideg.AnimationId = "https://www.roblox.com/assets/?id=94674093415095"
slideAnimRight.AnimationId = "https://www.roblox.com/assets/?id=103921112029675"
slideAnimLeft.AnimationId = "https://www.roblox.com/assets/?id=90335755885310"

char.Humanoid:GetPropertyChangedSignal("Jump"):Connect(function()
	uis.InputBegan:Connect(function(input)
		if input.KeyCode == Enum.KeyCode.LeftControl then
			
			if Keybinds.W.Value == true then
				local Slide = char.HumanoidRootPart:FindFirstChild("BodyVelocity")

				if Slide then
					Slide:Destroy()

					local playAnim = char.Humanoid:LoadAnimation(slideg)
					playAnim:Play()

					local newslide = Instance.new("BodyVelocity")
					newslide.MaxForce = Vector3.new(1,0,1) * 30000
					newslide.Velocity = char.HumanoidRootPart.CFrame.lookVector * 100
					newslide.Parent = char.HumanoidRootPart

					char.Humanoid.AutoRotate = true

					if script.Sound.Playing == false then
						script.Sound:Play()
					end

					for count = 1, 8 do
						wait(.1)
						newslide.Velocity *= .7

						char.Humanoid.HipHeight = -1.25
					end


					char.Humanoid.HipHeight = 0
					playAnim:Stop()

					newslide:Destroy()

					Keybinds.GSlide.Value = false
				end
			elseif Keybinds.S.Value == true then
				local Slide = char.HumanoidRootPart:FindFirstChild("BodyVelocity")

				if Slide then
					Slide:Destroy()

					local playAnim = char.Humanoid:LoadAnimation(slideg)
					playAnim:Play()

					local newslide = Instance.new("BodyVelocity")
					newslide.MaxForce = Vector3.new(1,0,1) * 30000
					newslide.Velocity = char.HumanoidRootPart.CFrame.lookVector * -100
					newslide.Parent = char.HumanoidRootPart

					char.Humanoid.AutoRotate = true

					if script.Sound.Playing == false then
						script.Sound:Play()
					end

					for count = 1, 8 do
						wait(.1)
						newslide.Velocity *= .7

						char.Humanoid.HipHeight = -1.25
					end


					char.Humanoid.HipHeight = 0
					playAnim:Stop()

					newslide:Destroy()

					Keybinds.GSlide.Value = false
				end
			elseif Keybinds.D.Value == true then
				local Slide = char.HumanoidRootPart:FindFirstChild("BodyVelocity")

				if Slide then
					Slide:Destroy()

					local playAnim = char.Humanoid:LoadAnimation(slideAnimRight)
					playAnim:Play()

					local newslide = Instance.new("BodyVelocity")
					newslide.MaxForce = Vector3.new(1,0,1) * 30000
					newslide.Velocity = char.HumanoidRootPart.CFrame.RightVector * 100
					newslide.Parent = char.HumanoidRootPart

					char.Humanoid.AutoRotate = true

					if script.Sound.Playing == false then
						script.Sound:Play()
					end

					for count = 1, 8 do
						wait(.1)
						newslide.Velocity *= .7

						char.Humanoid.HipHeight = -1.25
					end


					char.Humanoid.HipHeight = 0
					playAnim:Stop()

					newslide:Destroy()

					Keybinds.GSlide.Value = false
				end
			elseif Keybinds.A.Value == true then
				local Slide = char.HumanoidRootPart:FindFirstChild("BodyVelocity")

				if Slide then
					Slide:Destroy()

					local playAnim = char.Humanoid:LoadAnimation(slideAnimLeft)
					playAnim:Play()

					local newslide = Instance.new("BodyVelocity")
					newslide.MaxForce = Vector3.new(1,0,1) * 30000
					newslide.Velocity = char.HumanoidRootPart.CFrame.RightVector * -100
					newslide.Parent = char.HumanoidRootPart

					char.Humanoid.AutoRotate = true

					if script.Sound.Playing == false then
						script.Sound:Play()
					end

					for count = 1, 8 do
						wait(.1)
						newslide.Velocity *= .7

						char.Humanoid.HipHeight = -1.25
					end


					char.Humanoid.HipHeight = 0
					playAnim:Stop()

					newslide:Destroy()

					Keybinds.GSlide.Value = false
				end
			end

		end
	end)
end)

If anyone has a fix for this, or at least can patch up the script to make it work more efficiently, it’ll be greatly appreciated!

I haven’t fully read all the code, but I did notice you’re creating MULTIPLE listeners every time the “jump” variable changes, you may want to do something to disconnect/connect it only when you need it, something like this?:

local char = script.Parent.Parent
local slideg = Instance.new("Animation")
local slideAnimLeft = Instance.new("Animation")
local slideAnimRight = Instance.new("Animation")

local Keybinds = script.Parent.Keybinds
local uis = game:GetService("UserInputService")

local connection: RBXScriptConnection | nil = nil

slideg.AnimationId = "https://www.roblox.com/assets/?id=94674093415095"
slideAnimRight.AnimationId = "https://www.roblox.com/assets/?id=103921112029675"
slideAnimLeft.AnimationId = "https://www.roblox.com/assets/?id=90335755885310"

char.Humanoid:GetPropertyChangedSignal("Jump"):Connect(function()
	local humanoid: Humanoid = char.Humanoid;
	if (humanoid.Jump) then
		if (connection) then -- cleanup the old one
			connection:Disconnect()
		end
		connection = uis.InputBegan:Connect(function(input)
			if input.KeyCode == Enum.KeyCode.LeftControl then

				if Keybinds.W.Value == true then
					local Slide = char.HumanoidRootPart:FindFirstChild("BodyVelocity")

					if Slide then
						Slide:Destroy()

						local playAnim = char.Humanoid:LoadAnimation(slideg)
						playAnim:Play()

						local newslide = Instance.new("BodyVelocity")
						newslide.MaxForce = Vector3.new(1,0,1) * 30000
						newslide.Velocity = char.HumanoidRootPart.CFrame.lookVector * 100
						newslide.Parent = char.HumanoidRootPart

						char.Humanoid.AutoRotate = true

						if script.Sound.Playing == false then
							script.Sound:Play()
						end

						for count = 1, 8 do
							wait(.1)
							newslide.Velocity *= .7

							char.Humanoid.HipHeight = -1.25
						end


						char.Humanoid.HipHeight = 0
						playAnim:Stop()

						newslide:Destroy()

						Keybinds.GSlide.Value = false
					end
				elseif Keybinds.S.Value == true then
					local Slide = char.HumanoidRootPart:FindFirstChild("BodyVelocity")

					if Slide then
						Slide:Destroy()

						local playAnim = char.Humanoid:LoadAnimation(slideg)
						playAnim:Play()

						local newslide = Instance.new("BodyVelocity")
						newslide.MaxForce = Vector3.new(1,0,1) * 30000
						newslide.Velocity = char.HumanoidRootPart.CFrame.lookVector * -100
						newslide.Parent = char.HumanoidRootPart

						char.Humanoid.AutoRotate = true

						if script.Sound.Playing == false then
							script.Sound:Play()
						end

						for count = 1, 8 do
							wait(.1)
							newslide.Velocity *= .7

							char.Humanoid.HipHeight = -1.25
						end


						char.Humanoid.HipHeight = 0
						playAnim:Stop()

						newslide:Destroy()

						Keybinds.GSlide.Value = false
					end
				elseif Keybinds.D.Value == true then
					local Slide = char.HumanoidRootPart:FindFirstChild("BodyVelocity")

					if Slide then
						Slide:Destroy()

						local playAnim = char.Humanoid:LoadAnimation(slideAnimRight)
						playAnim:Play()

						local newslide = Instance.new("BodyVelocity")
						newslide.MaxForce = Vector3.new(1,0,1) * 30000
						newslide.Velocity = char.HumanoidRootPart.CFrame.RightVector * 100
						newslide.Parent = char.HumanoidRootPart

						char.Humanoid.AutoRotate = true

						if script.Sound.Playing == false then
							script.Sound:Play()
						end

						for count = 1, 8 do
							wait(.1)
							newslide.Velocity *= .7

							char.Humanoid.HipHeight = -1.25
						end


						char.Humanoid.HipHeight = 0
						playAnim:Stop()

						newslide:Destroy()

						Keybinds.GSlide.Value = false
					end
				elseif Keybinds.A.Value == true then
					local Slide = char.HumanoidRootPart:FindFirstChild("BodyVelocity")

					if Slide then
						Slide:Destroy()

						local playAnim = char.Humanoid:LoadAnimation(slideAnimLeft)
						playAnim:Play()

						local newslide = Instance.new("BodyVelocity")
						newslide.MaxForce = Vector3.new(1,0,1) * 30000
						newslide.Velocity = char.HumanoidRootPart.CFrame.RightVector * -100
						newslide.Parent = char.HumanoidRootPart

						char.Humanoid.AutoRotate = true

						if script.Sound.Playing == false then
							script.Sound:Play()
						end

						for count = 1, 8 do
							wait(.1)
							newslide.Velocity *= .7

							char.Humanoid.HipHeight = -1.25
						end


						char.Humanoid.HipHeight = 0
						playAnim:Stop()

						newslide:Destroy()

						Keybinds.GSlide.Value = false
					end
				end

			end
		end)
	else
		if (connection) then -- cleanup the old one
			connection:Disconnect()
		end
		connection = nil
	end 
end)

Though it might cause behavior issues, I’d make it cleanup 1-2 seconds after jumping

Also noticed your code doesn’t use DRY (dont repeat yourself) at all, and you could shorten the code a lot by saving a variable of what CFrame to use like so:

local char = script.Parent.Parent
local slideg = Instance.new("Animation")
local slideAnimLeft = Instance.new("Animation")
local slideAnimRight = Instance.new("Animation")

local Keybinds = script.Parent.Keybinds
local uis = game:GetService("UserInputService")

local connection: RBXScriptConnection | nil = nil

slideg.AnimationId = "https://www.roblox.com/assets/?id=94674093415095"
slideAnimRight.AnimationId = "https://www.roblox.com/assets/?id=103921112029675"
slideAnimLeft.AnimationId = "https://www.roblox.com/assets/?id=90335755885310"

char.Humanoid:GetPropertyChangedSignal("Jump"):Connect(function()
	local humanoid: Humanoid = char.Humanoid;
	if (humanoid.Jump) then
		if (connection) then -- cleanup the old one
			connection:Disconnect()
		end
		connection = uis.InputBegan:Connect(function(input)	
			if input.KeyCode == Enum.KeyCode.LeftControl then
				local humanoidRootPart: BasePart | Part = char.HumanoidRootPart
				local Slide: BodyVelocity | nil = humanoidRootPart:FindFirstChild("BodyVelocity") :: BodyVelocity
				local cframeToUse: Vector3 | nil = nil

				if (Keybinds.W.Value) then
					cframeToUse = humanoidRootPart.CFrame.LookVector * 100
				elseif (Keybinds.S.Value) then
					cframeToUse = humanoidRootPart.CFrame.LookVector * -100
				elseif (Keybinds.D.Value) then
					cframeToUse = humanoidRootPart.CFrame.RightVector * 100
				elseif (Keybinds.A.Value) then
					cframeToUse = humanoidRootPart.CFrame.RightVector * -100
				end

				if Slide and cframeToUse then
					Slide:Destroy()

					local playAnim = char.Humanoid:LoadAnimation(slideAnimRight)
					playAnim:Play()

					local newslide = Instance.new("BodyVelocity")
					newslide.MaxForce = Vector3.new(1,0,1) * 30000
					newslide.Velocity = cframeToUse
					newslide.Parent = char.HumanoidRootPart

					char.Humanoid.AutoRotate = true

					if script.Sound.Playing == false then
						script.Sound:Play()
					end

					for count = 1, 8 do
						task.wait(.1) -- task.wait is better
						newslide.Velocity *= .7
						char.Humanoid.HipHeight = -1.25
					end


					char.Humanoid.HipHeight = 0
					playAnim:Stop()
					newslide:Destroy()
					Keybinds.GSlide.Value = false
				end
			end
		end)
	else
		if (connection) then -- cleanup the old one
			connection:Disconnect()
		end
		connection = nil
	end 
end)

the g slide mechanic breaks whenever I use this script?
the script is basically so I can make chained slide jumps, if that can help you visualize

I would try doing the other idea I had of cleaning 1-2 seconds after:

local char = script.Parent.Parent
local slideg = Instance.new("Animation")
local slideAnimLeft = Instance.new("Animation")
local slideAnimRight = Instance.new("Animation")

local Keybinds = script.Parent.Keybinds
local uis = game:GetService("UserInputService")

local connection: RBXScriptConnection | nil = nil

slideg.AnimationId = "https://www.roblox.com/assets/?id=94674093415095"
slideAnimRight.AnimationId = "https://www.roblox.com/assets/?id=103921112029675"
slideAnimLeft.AnimationId = "https://www.roblox.com/assets/?id=90335755885310"

char.Humanoid:GetPropertyChangedSignal("Jump"):Connect(function()
	local humanoid: Humanoid = char.Humanoid;
	if (humanoid.Jump) then
		if (connection) then -- cleanup the old one
			connection:Disconnect()
		end
		
		connection = uis.InputBegan:Connect(function(input)	
			if input.KeyCode == Enum.KeyCode.LeftControl then
				local humanoidRootPart: BasePart | Part = char.HumanoidRootPart
				local Slide: BodyVelocity | nil = humanoidRootPart:FindFirstChild("BodyVelocity") :: BodyVelocity
				local cframeToUse: Vector3 | nil = nil

				if (Keybinds.W.Value) then
					cframeToUse = humanoidRootPart.CFrame.LookVector * 100
				elseif (Keybinds.S.Value) then
					cframeToUse = humanoidRootPart.CFrame.LookVector * -100
				elseif (Keybinds.D.Value) then
					cframeToUse = humanoidRootPart.CFrame.RightVector * 100
				elseif (Keybinds.A.Value) then
					cframeToUse = humanoidRootPart.CFrame.RightVector * -100
				end

				if Slide and cframeToUse then
					Slide:Destroy()

					local playAnim = char.Humanoid:LoadAnimation(slideAnimRight)
					playAnim:Play()

					local newslide = Instance.new("BodyVelocity")
					newslide.MaxForce = Vector3.new(1,0,1) * 30000
					newslide.Velocity = cframeToUse
					newslide.Parent = char.HumanoidRootPart

					char.Humanoid.AutoRotate = true

					if script.Sound.Playing == false then
						script.Sound:Play()
					end

					for count = 1, 8 do
						task.wait(.1) -- task.wait is better
						newslide.Velocity *= .7
						char.Humanoid.HipHeight = -1.25
					end


					char.Humanoid.HipHeight = 0
					playAnim:Stop()
					newslide:Destroy()
					Keybinds.GSlide.Value = false
				end
			end
		end)
		
		task.delay(1, function() 
			if (connection) then -- cleanup the old one
				connection:Disconnect()
			end
			connection = nil
		end)
	end 
end)
1 Like