I would like the player to slide of ledges (places where the Y level is higher than its surrounds).
I have looked for other solutions on the Developer Hub but nothing seems to match my problem.
local CAS = game:GetService("ContextActionService")
local UIS = game:GetService("UserInputService")
local ReplicatedStorage = game:GetService("ReplicatedStorage")
local tweenservice = game:GetService("TweenService")
local char = script.Parent
local slideAnim = script.SlideA
slideAnim.AnimationId = tostring(script:WaitForChild("SlideA").AnimationId)
local keybind = Enum.KeyCode.C
local shiftKey = Enum.KeyCode.LeftShift
local crouchKey = Enum.KeyCode.C
local acceleration = 35
local tweenedTransition = false
local slideControlFactor = 0.05 -- Adjust this value to change how much A/D affect the slide direction
local hrp = char:WaitForChild("HumanoidRootPart")
local hum = char:WaitForChild("Humanoid")
local slidingAttachment = Instance.new("Attachment")
slidingAttachment.Name = "SlidingAttachment"
slidingAttachment.Parent = hrp
local alignOrientation = Instance.new("AlignOrientation")
alignOrientation.Enabled = false
alignOrientation.RigidityEnabled = not tweenedTransition
alignOrientation.Mode = Enum.OrientationAlignmentMode.OneAttachment
alignOrientation.Attachment0 = slidingAttachment
alignOrientation.Parent = hrp
local canslide = true
local sliding = false
local shiftPressed = false
local controlPressed = false
local crouchPressed = false
local leftPressed = false
local rightPressed = false
-- Preload slide animation
local playAnim = hum:LoadAnimation(slideAnim)
playAnim.Looped = true
-- Create RaycastParams once to avoid recreating it every frame
local params = RaycastParams.new()
params.FilterDescendantsInstances = {char}
params.FilterType = Enum.RaycastFilterType.Exclude
local equippedTool = nil
local function stopSliding()
if not sliding then return end
sliding = false
alignOrientation.Enabled = false
hum.AutoRotate = true
hum:ChangeState(Enum.HumanoidStateType.GettingUp)
playAnim:Stop(0.5)
hum.CameraOffset = Vector3.zero
-- Re-equip the tool if it was equipped before
if equippedTool then
hum:EquipTool(equippedTool)
end
task.wait(0.5)
canslide = true
end
local function slideFunc()
if not canslide or hum.Health <= 0 or hum:GetState() ~= Enum.HumanoidStateType.Running or hum.WalkSpeed < 10 or hrp.Anchored then
return
end
canslide = false
sliding = true
alignOrientation.Enabled = true
hum:ChangeState(Enum.HumanoidStateType.Physics)
hrp.AssemblyLinearVelocity = hrp.CFrame.lookVector * acceleration
hum.AutoRotate = false
hum.CameraOffset = Vector3.new(0, -2.5, 0)
-- Store the tool that is currently equipped
equippedTool = nil
for _, tool in ipairs(char:GetChildren()) do
if tool:IsA("Tool") and tool.Parent == char then
equippedTool = tool
break
end
end
hum:UnequipTools()
playAnim:Play()
script.Slide:Play()
-- Reduce stamina on slide activation
while sliding and hrp.Velocity.Magnitude > 0.1 do
-- Adjust the shake intensity based on current speed
local speed = hrp.AssemblyLinearVelocity.Magnitude
local intensity = speed / 100 -- You can adjust the divisor to scale the intensity
task.wait()
end
stopSliding()
end
local function onInputBegan(input, gameProcessed)
if input.KeyCode == shiftKey then
shiftPressed = true
if crouchPressed then
end
elseif input.KeyCode == crouchKey then
controlPressed = true
if shiftPressed and not gameProcessed then
slideFunc()
end
elseif input.KeyCode == Enum.KeyCode.A then
leftPressed = true
elseif input.KeyCode == Enum.KeyCode.D then
rightPressed = true
end
end
local function onInputEnded(input, gameProcessed)
if input.KeyCode == shiftKey then
shiftPressed = false
if sliding then
stopSliding()
end
elseif input.KeyCode == crouchKey then
controlPressed = false
if sliding then
stopSliding()
end
elseif input.KeyCode == Enum.KeyCode.A then
leftPressed = false
elseif input.KeyCode == Enum.KeyCode.D then
rightPressed = false
end
end
UIS.InputBegan:Connect(onInputBegan)
UIS.InputEnded:Connect(onInputEnded)
local tweenInfo = TweenInfo.new(0.1)
game:GetService("RunService").RenderStepped:Connect(function()
if not sliding then return end
local result = workspace:Raycast(hrp.Position, Vector3.new(0, -4.5, 0), params)
local linearVelocity = hrp.AssemblyLinearVelocity
if result then
hrp.AssemblyLinearVelocity = linearVelocity - result.Normal * linearVelocity:Dot(result.Normal)
alignOrientation.CFrame = CFrame.lookAt(Vector3.zero, hrp.AssemblyLinearVelocity)
local currentRightVector = hrp.CFrame.RightVector
local upVector = result.Normal
local newFacialVector = currentRightVector:Cross(upVector)
local tween = tweenservice:Create(alignOrientation, tweenInfo, {
CFrame = CFrame.fromMatrix(hrp.Position, currentRightVector, upVector, newFacialVector)
})
tween:Play()
else
hrp.AssemblyLinearVelocity = Vector3.zero
end
-- Adjust direction based on player input
local slideDirection = hrp.CFrame.lookVector
if leftPressed then
slideDirection = slideDirection - hrp.CFrame.RightVector * slideControlFactor
elseif rightPressed then
slideDirection = slideDirection + hrp.CFrame.RightVector * slideControlFactor
end
-- Normalize slide direction to ensure it stays on the slope
slideDirection = (slideDirection - result.Normal * slideDirection:Dot(result.Normal)).Unit
hrp.AssemblyLinearVelocity = slideDirection * hrp.AssemblyLinearVelocity.Magnitude
end)
![2024-06-07-14-09-45_3xa9eFln|video](upload://8KnnXbovqVu3x7qDfb1YMhAhE0B.mp4)