Wall jumping error 3d

okay i have a custom third person controller and when i was playing around with it in my game to see if it was working right i came across a problem wall jump works fine but if i stand in one place ( like the middle of the stage) and start jumping ( mashing jump button) then start moving toward a wall he goes straight up it im trying to make him jump hit a wall turn around jump off other wall (it works fine) just the standing in one spot and mashing jump makes him able to climb walls with out haveing to to wall jump off another wall? my game is 3D or 2.5 d
i dont know the dif?

HERE’S THE SCRIPT

using UnityEngine;
using System.Collections;

public class ThirdPersonController : MonoBehaviour {
   
    public AnimationClip idleAnimation;
    public AnimationClip fallAnimanton;
    public AnimationClip walkAnimation;
    public AnimationClip runAnimation;
    public AnimationClip jumpPoseAnimation;
    public AnimationClip edgeAnimation;
    public AnimationClip slamAnimation;
   
    public float walkMaxAnimationSpeed = 0.50f;
    public float trotMaxAnimationSpeed = 0.70f;
    public float runMaxAnimationSpeed = 1.0f;
    public float jumpAnimationSpeed = 1.15f;
    public float fallAnimationSpeed = 1.0f;
    public float edgeAnimationSpeed = 1.0f;
    public float slamAnimationSpeed = 1.0f;
   
    public float magnitude;
    public float vel = 1;
   
    private Animation _animation;
   
    public enum CharacterState {
        Idle = 0,
        Walking = 1,
        Trotting = 2,
        Running = 3,
        Jumping = 4,
        edge = 5,
        slam = 1,
    }
   
    public CharacterState _characterState;
   
    // The speed when walking
    float walkSpeed= 1.0f;
    // after trotAfterSeconds of walking we trot with trotSpeed
    float trotSpeed= 2.0f;
    // when pressing "Fire3" button (cmd) we start running
    float runSpeed= 3.0f;
   
    float inAirControlAcceleration= 3.0f;
   
    // How high do we jump when pressing jump and letting go immediately
    public float jumpHeight= 0.5f;
   
    // We add extraJumpHeight meters on top when holding the button down longer while jumping
    public float extraJumpHeight = 2.5f;
   
    // The gravity for the character
    float gravity= 20.0f;
    float controlledDescentGravity = 10.0f;
    // The gravity in controlled descent mode
    float speedSmoothing= 10.0f;
    float rotateSpeed= 500.0f;
    float trotAfterSeconds= 3.0f;
   
    bool canJump= true;
    bool canControlDescent = true;
    bool canWallJump = true;
   
    private float jumpRepeatTime= 0.05f;
    private float jumpTimeout= 0.15f;
    private float groundedTimeout= 0.25f;
    private float wallJumpTimeout = 0.15f;
   
    // The camera doesnt start following the target immediately but waits for a split second to avoid too much waving around.
    private float lockCameraTimer= 0.0f;
   
    // The current move direction in x-z
    private Vector3 moveDirection= Vector3.zero;
    // The current vertical speed
    private float verticalSpeed= 0.0f;
    // The current x-z move speed
    private float moveSpeed= 0.0f;
   
    // The last collision flags returned from controller.Move
    private CollisionFlags collisionFlags;
   
    // Are we jumping? (Initiated with jump button and not grounded yet)
    public static bool jumping= false;
    private bool jumpingReachedApex= false;
   
    // Are we moving backwards (This locks the camera to not do a 180 degree spin)
    private bool movingBack= false;
    // Is the user pressing any keys?
    private bool isMoving= false;
    // When did the user start walking (Used for going into trot after a while)
    private float walkTimeStart= 0.0f;
    // Last time the jump button was clicked down
    private float lastJumpButtonTime= -10.0f;
    // Last time we performed a jump
    private float lastJumpTime= -1.0f;
   
   
    // the height we jumped from (Used to determine for how long to apply extra jump power after jumping.)
    private float lastJumpStartHeight= 0.0f;
   
   
    public static Vector3 inAirVelocity= Vector3.zero;
   
    private float lastGroundedTime= 0.0f;
   
   
    private bool isControllable= true;
   
   
   
    // Average normal of the last touched geometry
    Vector3 wallJumpContactNormal;
    private float wallJumpContactNormalHeight;
    // When did we touch the wall the first time during this jump (Used for wall jumping)
    private float touchWallJumpTime = -1.0f;
   
    //Are we on a ledge
    public static Transform ledgeTransform;
    public static bool onLedge = false;
   
    private float lean = 0.0f;
    private bool slammed = false;
   
   
    void  Awake (){
        moveDirection = transform.TransformDirection(Vector3.forward);
       
        _animation = GetComponent<Animation>();
        if(!_animation)
            Debug.Log("The character you would like to control doesn't have animations. Moving her might look weird.");
       
        if(!idleAnimation) {
            _animation = null;
            Debug.Log("No idle animation found. Turning off animations.");
        }
        if(!walkAnimation) {
            _animation = null;
            Debug.Log("No walk animation found. Turning off animations.");
        }
        if(!runAnimation) {
            _animation = null;
            Debug.Log("No run animation found. Turning off animations.");
        }
        if(!jumpPoseAnimation && canJump) {
            _animation = null;
            Debug.Log("No jump animation found and the character has canJump enabled. Turning off animations.");
        }
       
    }
   
   
   
    void OnTriggerEnter(Collider other)
    {
       
    }
   
   
   
    void  UpdateSmoothedMovementDirection ()
    {
        Transform cameraTransform= Camera.main.transform;
        bool grounded= IsGrounded();
       
        // Forward vector relative to the camera along the x-z plane   
        Vector3 forward= cameraTransform.TransformDirection(Vector3.forward);
        forward.y = 0;
        forward = forward.normalized;
       
        // Right vector relative to the camera
        // Always orthogonal to the forward vector
        Vector3 right = new Vector3(forward.z, 0, -forward.x);
       
        float v = Input.GetAxisRaw("Vertical");
        float h = Input.GetAxisRaw("Horizontal");
       
        // Are we moving backwards or looking backwards
        if (v < -0.2f)
            movingBack = true;
        else
            movingBack = false;
       
        bool wasMoving= isMoving;
        isMoving = Mathf.Abs (h) > 0.1f || Mathf.Abs (v) > 0.1f;
       
        // Target direction relative to the camera
        Vector3 targetDirection= h * right + v * forward;
       
        // Smooth the speed based on the current target direction
        float curSmooth= speedSmoothing * Time.deltaTime;
       
        // Choose target speed
        //* We want to support analog input but make sure you cant walk faster diagonally than just forward or sideways
        float targetSpeed= Mathf.Min(targetDirection.magnitude, 1.0f);
       
        if (onLedge && ledgeTransform)
        {
            _characterState = CharacterState.edge;
            // Lock camera for short period when transitioning moving & standing still
            lockCameraTimer += Time.deltaTime;
            if (isMoving != wasMoving)
                lockCameraTimer = 0.0f;
           
            // We store speed and direction seperately,
            // so that when the character stands still we still have a valid forward direction
            // moveDirection is always normalized, and we only update it if there is user input.
            //If the camera is behind/beside, right is right. Otherwise, right is left.
            if(Vector3.Dot(Camera.main.transform.forward, transform.forward) < 0)
                moveDirection = h * ledgeTransform.right;
            else
                moveDirection = h * -ledgeTransform.right;
           
            // Pick speed modifier
            if (Input.GetButton ("Fire3"))
            {
                targetSpeed *= runSpeed;
            }
            else if (Time.time - trotAfterSeconds > walkTimeStart)
            {
                targetSpeed *= trotSpeed;
            }
            else
            {
                targetSpeed *= walkSpeed;
            }
           
            moveSpeed = Mathf.Lerp(moveSpeed, targetSpeed, curSmooth);
           
            // Reset walk time start when we slow down
            if (moveSpeed < walkSpeed * 0.3)
                walkTimeStart = Time.time;
        }
       
        // Grounded controls
        else if (grounded)
        {
            // Lock camera for short period when transitioning moving & standing still
            lockCameraTimer += Time.deltaTime;
            if (isMoving != wasMoving)
                lockCameraTimer = 0.0f;
           
            // We store speed and direction seperately,
            // so that when the character stands still we still have a valid forward direction
            // moveDirection is always normalized, and we only update it if there is user input.
            if (targetDirection != Vector3.zero)
            {
                // If we are really slow, just snap to the target direction
                if (moveSpeed < walkSpeed * 0.9f && grounded)
                {
                    moveDirection = targetDirection.normalized;
                }
                // Otherwise smoothly turn towards it
                else
                {
                    moveDirection = Vector3.RotateTowards(moveDirection, targetDirection, rotateSpeed * Mathf.Deg2Rad * Time.deltaTime, 1000);
                   
                    moveDirection = moveDirection.normalized;
                }
            }
            _characterState = CharacterState.Idle;
           
            // Pick speed modifier
            if (Input.GetKey (KeyCode.LeftShift) || Input.GetKey (KeyCode.RightShift))
            {
                targetSpeed *= runSpeed;
                _characterState = CharacterState.Running;
                if(magnitude > 0.1f)
                    vel = 2;
            }
            else if (Time.time - trotAfterSeconds > walkTimeStart)
            {
                targetSpeed *= trotSpeed;
                _characterState = CharacterState.Trotting;
                vel = 1.4f;
            }
            else
            {
                targetSpeed *= walkSpeed;
                _characterState = CharacterState.Walking;
                vel = 1;
            }
           
            moveSpeed = Mathf.Lerp(moveSpeed, targetSpeed, curSmooth);
           
            // Reset walk time start when we slow down
            if (moveSpeed < walkSpeed * 0.3f)
                walkTimeStart = Time.time;
        }
        // In air controls
        else
        {
            // Lock camera while in air
            if (jumping)
                lockCameraTimer = 0.0f;
           
            if (isMoving)
                inAirVelocity += targetDirection.normalized * Time.deltaTime * inAirControlAcceleration;
        }
       
       
       
    }
   
    void ApplyWallJump ()
    {
        // We must actually jump against a wall for this to work
        if (!jumping)
            return;
       
        // Store when we first touched a wall during this jump
        if (collisionFlags == CollisionFlags.CollidedSides)
        {
            touchWallJumpTime = Time.time;
        }
       
        // The user can trigger a wall jump by hitting the button shortly before or shortly after hitting the wall the first time.
        var mayJump = lastJumpButtonTime > touchWallJumpTime - wallJumpTimeout && lastJumpButtonTime < touchWallJumpTime + wallJumpTimeout;
        if (!mayJump)
            return;
       
        // Prevent jumping too fast after each other
        if (lastJumpTime + jumpRepeatTime > Time.time)
            return;
       
       
        if (Mathf.Abs(wallJumpContactNormal.y) < 0.2)
        {
            wallJumpContactNormal.y = 0;
            moveDirection = wallJumpContactNormal.normalized;
            // Wall jump gives us at least trotspeed
            moveSpeed = Mathf.Clamp(moveSpeed * 1.5f, trotSpeed, runSpeed);
        }
        else
        {
            moveSpeed = 0;
        }
       
        verticalSpeed = CalculateJumpVerticalSpeed (jumpHeight);
        DidJump();
        SendMessage("DidWallJump", null, SendMessageOptions.DontRequireReceiver);
    }
   
    void  ApplyJumping (){
        // Prevent jumping too fast after each other
        if (lastJumpTime + jumpRepeatTime > Time.time)
            return;
       
        if (IsGrounded()) {
            // Jump
            // - Only when pressing the button down
            // - With a timeout so you can press the button slightly before landing       
            if (canJump && Time.time < lastJumpButtonTime + jumpTimeout) {
                verticalSpeed = CalculateJumpVerticalSpeed (jumpHeight);
                SendMessage("DidJump", SendMessageOptions.DontRequireReceiver);
            }
        }
    }
   
   
    void  ApplyGravity (){
        if (isControllable)    // don't move player at all if not controllable.
        {
            // Apply gravity
            bool jumpButton= Input.GetButton("Jump");
           
            // * When falling down we use controlledDescentGravity (only when holding down jump)
            bool controlledDescent = canControlDescent && verticalSpeed <= 0.0f && jumpButton && jumping;
           
            // When we reach the apex of the jump we send out a message
            if (jumping && !jumpingReachedApex && verticalSpeed <= 0.0f)
            {
                jumpingReachedApex = true;
                SendMessage("DidJumpReachApex", SendMessageOptions.DontRequireReceiver);
            }
           
            // * When jumping up we don't apply gravity for some time when the user is holding the jump button
            // This gives more control over jump height by pressing the button longer
            bool extraPowerJump = IsJumping () && verticalSpeed > 0.0f && jumpButton && transform.position.y < lastJumpStartHeight + extraJumpHeight;
           
            //Let go of the ledge
            if (onLedge && jumpButton)
            {
                onLedge = false;
                moveDirection = transform.forward;
                movingBack = true;
            }
           
            if (controlledDescent)
                verticalSpeed -= controlledDescentGravity * Time.deltaTime;
            else if (extraPowerJump)
                return;   
            else if (IsGrounded ()|| onLedge)
                verticalSpeed = 0.0f;
            else
                verticalSpeed -= gravity * Time.deltaTime;
        }
    }
   
    float  CalculateJumpVerticalSpeed ( float targetJumpHeight  ){
        // From the jump height and gravity we deduce the upwards speed
        // for the character to reach at the apex.
        return Mathf.Sqrt(2 * targetJumpHeight * gravity);
    }
   
    void  DidJump (){
        jumping = true;
        jumpingReachedApex = false;
        lastJumpTime = Time.time;
        lastJumpStartHeight = transform.position.y;
        touchWallJumpTime = -1;
        lastJumpButtonTime = -10;
       
        _characterState = CharacterState.Jumping;
    }
   
    void  Update (){
       
        if (!isControllable)
        {
            // kill all inputs if not controllable.
            Input.ResetInputAxes();
        }
       
        if (Input.GetButtonDown ("Jump"))
        {
            lastJumpButtonTime = Time.time;
        }
       
        UpdateSmoothedMovementDirection();
       
        // Apply gravity
        // - extra power jump modifies gravity
        // - controlledDescent mode modifies gravity
        ApplyGravity ();
       
        // Perform a wall jump logic
        // - Make sure we are jumping against wall etc.
        // - Then apply jump in the right direction)
        if (canWallJump)
            ApplyWallJump();
        // Apply jumping logic
        ApplyJumping ();
       
        // Calculate actual motion
        Vector3 movement = moveDirection * moveSpeed + new Vector3 (0, verticalSpeed, 0) + inAirVelocity;
        movement *= Time.deltaTime;//moveDirection * moveSpeed + Vector3 (0, verticalSpeed, 0) + inAirVelocity
       
        magnitude = movement.magnitude;
       
       
        // Move the controller
        CharacterController controller = GetComponent<CharacterController>();
        wallJumpContactNormal = Vector3.zero;
        collisionFlags = controller.Move(movement);
       
        // ANIMATION sector
        if(_animation) {
            if(_characterState == CharacterState.edge)
            {
                _animation[edgeAnimation.name].speed = edgeAnimationSpeed;
                _animation[edgeAnimation.name].wrapMode = WrapMode.ClampForever;
                _animation.CrossFade(edgeAnimation.name);
               
            }
            if(_characterState == CharacterState.Jumping)
            {
                if(!jumpingReachedApex) {
                    _animation[jumpPoseAnimation.name].speed = jumpAnimationSpeed;
                    _animation[jumpPoseAnimation.name].wrapMode = WrapMode.ClampForever;
                    _animation.CrossFade(jumpPoseAnimation.name);
                } else {
                    _animation[fallAnimanton.name].speed = -fallAnimationSpeed;
                    _animation[fallAnimanton.name].wrapMode = WrapMode.ClampForever;
                    _animation.CrossFade(fallAnimanton.name);               
                }
            }
            else
            {
                if(controller.velocity.sqrMagnitude < 0.1f) {
                    _animation.CrossFade(idleAnimation.name);
                }
                else
                {
                    if(_characterState == CharacterState.Running) {
                        _animation[runAnimation.name].speed = Mathf.Clamp(controller.velocity.magnitude, 0.0f, runMaxAnimationSpeed);
                        _animation.CrossFade(runAnimation.name);   
                    }
                    else if(_characterState == CharacterState.Trotting) {
                        _animation[walkAnimation.name].speed = Mathf.Clamp(controller.velocity.magnitude, 0.0f, trotMaxAnimationSpeed);
                        _animation.CrossFade(walkAnimation.name);   
                    }
                    else if(_characterState == CharacterState.Walking) {
                        _animation[walkAnimation.name].speed = Mathf.Clamp(controller.velocity.magnitude, 0.0f, walkMaxAnimationSpeed);
                        _animation.CrossFade(walkAnimation.name);   
                    }
                   
                }
            }
        }
        // ANIMATION sector
       
        if(onLedge && ledgeTransform)
        {
            transform.rotation = Quaternion.LookRotation(-ledgeTransform.forward);
        }
       
        // Set rotation to the move direction
        else if (IsGrounded())
        {
            if(slammed) // we got knocked over by an enemy. We need to reset some stuff
            {
                slammed = false;
                controller.height = 2;
                Vector3 temp = transform.position; // copy to an auxiliary variable...
                temp.y = 0.75f; // modify the component you want in the variable...
            }
           
            transform.rotation = Quaternion.LookRotation(moveDirection);
           
        }   
        else
        {
            if(!slammed)
            {
                Vector3 xzMove= movement;
                xzMove.y = 0;
                if (xzMove.sqrMagnitude > 0.001f)
                {
                    transform.rotation = Quaternion.LookRotation(xzMove);
                }
            }
        }   
       
        // We are in jump mode but just became grounded
        if (IsGrounded())
        {
            lastGroundedTime = Time.time;
            inAirVelocity = Vector3.zero;
            if (jumping)
            {
                jumping = false;
                SendMessage("DidLand", SendMessageOptions.DontRequireReceiver);
            }
        }
    }
   
    void  OnControllerColliderHit ( ControllerColliderHit hit   ){
        //    Debug.DrawRay(hit.point, hit.normal);
        if (hit.moveDirection.y > 0.01f)
            return;
        wallJumpContactNormal = hit.normal;
    }
   
    float  GetSpeed (){
        return moveSpeed;
    }
   
    public bool  IsJumping (){
        return jumping;
    }
   
    bool  IsGrounded (){
        return (collisionFlags & CollisionFlags.CollidedBelow) != 0;
    }
   
    void SuperJump (float height)
    {
        verticalSpeed = CalculateJumpVerticalSpeed (height);
        collisionFlags = CollisionFlags.None;
        SendMessage("DidJump", SendMessageOptions.DontRequireReceiver);
    }
   
    void SuperJump (float height, Vector3 jumpVelocity)
    {
        verticalSpeed = CalculateJumpVerticalSpeed (height);
        inAirVelocity = jumpVelocity;
       
        collisionFlags = CollisionFlags.None;
        SendMessage("DidJump", SendMessageOptions.DontRequireReceiver);
    }
   
    void Slam (Vector3 direction)
    {
        verticalSpeed = CalculateJumpVerticalSpeed (1);
        inAirVelocity = direction * 6;
        direction.y = 0.6f;
        Quaternion.LookRotation(-direction);
        CharacterController controller  = GetComponent<CharacterController>();
        controller.height = 0.5f;
        slammed = true;
        collisionFlags = CollisionFlags.None;
        SendMessage("DidJump", SendMessageOptions.DontRequireReceiver);
    }
   
    public void GrabLedge(Transform ledge)
    {
        ledgeTransform = ledge;
        onLedge = true;
        jumping = false;
        inAirVelocity = Vector3.zero;
       
    }
   
    Vector3  GetDirection (){
        return moveDirection;
    }
   
    public bool  IsMovingBackwards (){
        return movingBack;
    }
   
    public float  GetLockCameraTimer ()
    {
        return lockCameraTimer;
    }
   
    bool IsMoving ()
    {
        return Mathf.Abs(Input.GetAxisRaw("Vertical")) + Mathf.Abs(Input.GetAxisRaw("Horizontal")) > 0.5f;
    }
   
    bool  HasJumpReachedApex ()
    {
        return jumpingReachedApex;
    }
   
    bool  IsGroundedWithTimeout ()
    {
        return lastGroundedTime + groundedTimeout > Time.time;
    }
   
    bool IsControlledDescent ()
    {
        // * When falling down we use controlledDescentGravity (only when holding down jump)
        bool jumpButton = Input.GetButton("Jump");
        return canControlDescent && verticalSpeed <= 0.0 && jumpButton && jumping;
    }
   
    void  Reset ()
    {
        gameObject.tag = "Player";
    }
   
}

Read this first

Well now i know lol thx :slight_smile: