- Home /
 
Slope sliding mechanism problem
I'm using an adapted version of the FPSWalkerEnhanced script (http://wiki.unity3d.com/index.php?title=FPSWalkerEnhanced). This is my code:
 using System.Collections;
 using System.Collections.Generic;
 using UnityEngine;
 using UnityEditor;
 
 public class PlayerController : MonoBehaviour {
     public CameraController cameraController;
     private CharacterController controller;
     private Transform myTransform;
 
     private float speedX = 0;
     private float speedY = 0;
     private float speedZ = 0;
     private float moveX = 0;
     private float moveZ = 0;
 
     public float acceleration;
     public float decelleration;
     public float walkSpeed;
     public float runSpeed;
     public float gravity;
 
     private float slideLimit;
     private float rayDistance;
     private bool grounded = false;
 
     private Vector3 moveDirection;
     private Vector3 contactPoint;
     private RaycastHit hit;
 
     public float antiBumpFactor = .75f;
 
     void Start () {
         controller = GetComponent<CharacterController>();
         myTransform = transform;
         rayDistance = controller.height * .5f + controller.radius;
         slideLimit = controller.slopeLimit - .1f;
     }
     
     void FixedUpdate () {
         float maxSpeed = Input.GetButton("Run")? runSpeed : walkSpeed;
         float direction = (180 + cameraController.GetViewDirection()) * Mathf.Deg2Rad;
         float forward = (Input.GetKey("w") ? 1 : 0) + (Input.GetKey("s") ? -1 : 0);
         float right = (Input.GetKey("d") ? 1 : 0) + (Input.GetKey("a") ? -1 : 0);
         moveX = Mathf.Sin(direction) * right + Mathf.Cos(direction) * forward;
         moveZ = Mathf.Sin(direction) * forward - Mathf.Cos(direction) * right;
 
         float ratio = Mathf.Sqrt (Mathf.Pow(moveX, 2) + Mathf.Pow(moveZ, 2))/maxSpeed;
         if (ratio != 0) {
             moveX = moveX / ratio;
             moveZ = moveZ / ratio;
         }
 
         if (moveX > speedX)
             speedX = Mathf.Min (speedX + acceleration*Time.deltaTime, moveX);
         else if (moveX < speedX)
             speedX = Mathf.Max (speedX - decelleration*Time.deltaTime, moveX);
 
         if (moveZ > speedZ)
             speedZ = Mathf.Min (speedZ + acceleration*Time.deltaTime, moveZ);
         else if (moveZ < speedZ)
             speedZ = Mathf.Max (speedZ - decelleration*Time.deltaTime, moveZ);
 
         moveDirection = new Vector3 (speedX, 0, speedZ);
         
         if (grounded) {
                         //sliding stuff
             bool sliding = false;
             if (Physics.Raycast(myTransform.position, -Vector3.up, out hit, rayDistance)) {
                 if (Vector3.Angle(hit.normal, Vector3.up) > slideLimit)
                     sliding = true;
             } else {
                 Physics.Raycast(contactPoint + Vector3.up, -Vector3.up, out hit);
                 if (Vector3.Angle(hit.normal, Vector3.up) > slideLimit)
                     sliding = true;
             }
 
             if (sliding) {
                 print ("true");
                 Vector3 hitNormal = hit.normal;
                 moveDirection = new Vector3(hitNormal.x, -hitNormal.y, hitNormal.z);
                 Vector3.OrthoNormalize (ref hitNormal, ref moveDirection);
                 moveDirection *= 5;
             } else {
                 print ("false");
                 moveDirection.y = -antiBumpFactor;
             }
         }
         moveDirection.y -= gravity;
 
         grounded = (controller.Move(moveDirection*Time.deltaTime) & CollisionFlags.Below) != 0;
     }
 
     void OnControllerColliderHit (ControllerColliderHit hit) {
         contactPoint = hit.point;
     }
 }
 
               However, the sliding mechanism glitches out edges of cubes and planes, making it impossible to jump down from them. 
 I am new to unity, so I'm finding it hard to solve this problem. Does anyone know a solution?
Answer by j0nk · Apr 17, 2018 at 01:46 PM
After some debugging I found out that the RayCast was colliding with the character's own controller. This was solved by adding a condition:
 if (Physics.Raycast(myTransform.position, -Vector3.up, out hit, rayDistance)) {
                 if (Vector3.Angle (hit.normal, Vector3.up) > slideLimit && hit.collider != controller) 
                     sliding = true;
             } else {
                 Physics.Raycast(contactPoint + Vector3.up, -Vector3.up, out hit);
                 if (Vector3.Angle (hit.normal, Vector3.up) > slideLimit && hit.collider != controller)
                     sliding = true;
             }
 
              Your answer
 
             Follow this Question
Related Questions
How to add a value to a Raycast Vector 1 Answer
Gravity makes player slide on any slope!!! Check if rigidbody Isgrounded not working 0 Answers
Sliding Problem Tomb Raider like game C# 1 Answer
How to make third person character aim at object in front of camera? 1 Answer
Spawning object by using ray 1 Answer