I have a wall climbing system that is working quite perfectly except for one part.
I am trying to apply this mechanism:
and it detects it correctly but pretty buggy, here is a video to see what I mean:
here is the code:
function WallClimb:GetClimbCFrame(raycastResult)
local lookVector, rightVector, upVector, position
local isBelowAnyBall = false
for _, ball in ipairs(Balls:GetChildren()) do
if raycastResult.Position.Y < (ball.Position.Y - 5) then
isBelowAnyBall = true
end
end
if isBelowAnyBall then
self.IsBelow = true
lookVector = self.Super.HumanoidRootPart.CFrame.LookVector
else
self.IsBelow = false
lookVector = raycastResult.Normal * -1
end
rightVector = lookVector:Cross(Vector3.yAxis).Unit
upVector = rightVector:Cross(lookVector).Unit
position = raycastResult.Position + (raycastResult.Normal * self.HoldDistanceFromWall)
return CFrame.fromMatrix(position, rightVector, upVector)
end
function WallClimb:GetMoveVector(cframe, raycastResult)
local normalCFrame = cframe * CFrame.Angles(math.pi / -2, 0, 0)
local moveDirection = self.Super.Humanoid.MoveDirection
local relativeMoveDirection = workspace.CurrentCamera.CFrame.Rotation:PointToObjectSpace(moveDirection)
relativeMoveDirection *= Vector3.new(1, 0, -1)
if relativeMoveDirection.Magnitude > 0 then
relativeMoveDirection = relativeMoveDirection.Unit
end
local moveVector = normalCFrame.Rotation:PointToWorldSpace(relativeMoveDirection)
return moveVector
end
function WallClimb:StartClimbing(raycastResult, headRaycastResult, deltaTime)
local isBelowAnyBall = false
for _, ball in ipairs(Balls:GetChildren()) do
if raycastResult.Position.Y < (ball.Position.Y - 5) then
isBelowAnyBall = true
break
end
end
if isBelowAnyBall then
self.PlayingAnimation:Stop()
if self.PlayingAnimation ~= self.ClimbingAnimation2 then
self.PlayingAnimation = self.ClimbingAnimation2
self.PlayingAnimation:Play()
end
else
self.PlayingAnimation:Stop()
if self.PlayingAnimation ~= self.ClimbingAnimation then
self.PlayingAnimation = self.ClimbingAnimation
self.PlayingAnimation:Play()
end
end
if not self.IsClimbing then
self.IsClimbing = true
end
local framerate = 60
local timeMultiplier = deltaTime * framerate
local cframe = raycastResult and self:GetClimbCFrame(raycastResult) or self.CFrame
local moveVector = self:GetMoveVector(cframe, raycastResult)
self.CFrame = cframe
self.CFrame += moveVector * self.ClimbSpeed * deltaTime
self.Super.HumanoidRootPart.Anchored = true
if self.IsBelow and headRaycastResult then
cframe = self:GetClimbCFrame(headRaycastResult)
moveVector = self:GetMoveVector(cframe, headRaycastResult)
end
self.PlayingAnimation:AdjustSpeed(moveVector.Magnitude * self.AnimationSpeed)
self.Super.HumanoidRootPart.CFrame = self.Super.HumanoidRootPart.CFrame:Lerp(self.CFrame, self.MoveLerp * timeMultiplier)
end
I would apperciate the help!