Example #1
0
        private void TriggerMovementSounds(FootstepSurfaceInfo surfaceInfo, bool isLeftFoot)
        {
            MovementType movementType;

            if (isCrouched)
            {
                if (currentAnimatorVelocity >= runLimit + crouchedRunAdjustment)
                {
                    if (isGoingUpTheStairs)
                    {
                        movementType = MovementType.RunCrouchedStairsUp;
                    }
                    else if (isGoingDownTheStairs)
                    {
                        movementType = MovementType.RunCrouchedStairsDown;
                    }
                    else
                    {
                        movementType = MovementType.RunCrouched;
                    }
                }
                else
                {
                    if (isGoingUpTheStairs)
                    {
                        movementType = MovementType.WalkCrouchedStairsUp;
                    }
                    else if (isGoingDownTheStairs)
                    {
                        movementType = MovementType.WalkCrouchedStairsDown;
                    }
                    else
                    {
                        movementType = MovementType.WalkCrouched;
                    }
                }
            }
            else if (currentAnimatorVelocity >= runLimit)
            {
                if (isGoingUpTheStairs)
                {
                    movementType = MovementType.RunStairsUp;
                }
                else if (isGoingDownTheStairs)
                {
                    movementType = MovementType.RunStairsDown;
                }
                else
                {
                    movementType = MovementType.Run;
                }
            }
            else
            {
                if (isGoingUpTheStairs)
                {
                    movementType = MovementType.WalkStairsUp;
                }
                else if (isGoingDownTheStairs)
                {
                    movementType = MovementType.WalkStairsDown;
                }
                else
                {
                    movementType = MovementType.Walk;
                }
            }

            if (isLeftFoot)
            {
                PlayFootstep(movementType, surfaceInfo.surfaceType, leftFootPosition);

                if (foleyPosition != null)
                {
                    PlayFoley(movementType, foleyPosition);
                }

                if (surfaceInfo.layerType != SurfaceLayerType.None)
                {
                    PlayLayer(movementType, surfaceInfo.layerType, leftFootPosition);
                }
            }
            else
            {
                PlayFootstep(movementType, surfaceInfo.surfaceType, rightFootPosition);

                if (foleyPosition != null)
                {
                    PlayFoley(movementType, foleyPosition);
                }

                if (surfaceInfo.layerType != SurfaceLayerType.None)
                {
                    PlayLayer(movementType, surfaceInfo.layerType, rightFootPosition);
                }
            }
        }
Example #2
0
        private void FootstepUpdate()
        {
            // In addition to aborting the regular footstep update check when the player is not grounded one should add all the other applicable game specific checks here.
            // <- Could involve movement types such as climbing, vaulting or any kind of deterministic animation sequence with their own sfx triggering requirements.
            if (!isGrounded)
            {
                previousLeftFootDirection  = 0;
                previousRightFootDirection = 0;
                previousLeftFootHeight     = 0;
                previousRightFootHeight    = 0;
                hasRaisedLeftFoot          = false;
                hasRaisedRightFoot         = false;

                isMoving = false;
                StopAllCoroutines();
                sidleCooldownInProgress = false;
                return;
            }

            float leftHeight  = GetFootHeight(true);
            float rightHeight = GetFootHeight(false);

            if (leftHeight == int.MaxValue || rightHeight == int.MaxValue || leftHeight < 0 || rightHeight < 0)
            {
                // Feet height checks failed.
                return;
            }

            #if UNITY_EDITOR
            var roundLeft = Math.Round(leftHeight, 2);
            leftHeightDebug = roundLeft.ToString();
            var roundRight = Math.Round(rightHeight, 2);
            rightHeightDebug = roundRight.ToString();
            var roundVelocity = Math.Round(currentAnimatorVelocity, 2);
            velocityDebug = roundVelocity.ToString();
            #endif

            bool footstepTriggered = false;

            int leftFootDirection;
            int rightFootDirection;

            if (leftHeight > previousLeftFootHeight)
            {
                leftFootDirection = 1;
            }
            else if (leftHeight < previousLeftFootHeight)
            {
                leftFootDirection = -1;
            }
            else
            {
                leftFootDirection = previousLeftFootDirection;
            }

            if (rightHeight > previousRightFootHeight)
            {
                rightFootDirection = 1;
            }
            else if (rightHeight < previousRightFootHeight)
            {
                rightFootDirection = -1;
            }
            else
            {
                rightFootDirection = previousRightFootDirection;
            }

            if (leftHeight > thresholdHeight && !hasRaisedLeftFoot)
            {
                hasRaisedLeftFoot = true;
            }
            else if (isCrouched && leftHeight > (thresholdHeight + crouchedThresholdAdjustment) && !hasRaisedLeftFoot)
            {
                hasRaisedLeftFoot = true;
            }
            else if (leftHeight < distanceWhenGrounded && hasRaisedLeftFoot)
            {
                hasRaisedLeftFoot = false;

                if (leftFootDirection < 0)
                {
                    if (currentAnimatorVelocity > walkLimit)
                    {
                        footstepTriggered = true;
                        FootstepSurfaceInfo surfaceInfo = CheckCurrentSurface(leftFootPosition);
                        TriggerMovementSounds(surfaceInfo, true);
                    }
                    else if (isCrouched && currentAnimatorVelocity >= (walkLimit + crouchedWalkAdjustment))
                    {
                        footstepTriggered = true;
                        FootstepSurfaceInfo surfaceInfo = CheckCurrentSurface(leftFootPosition);
                        TriggerMovementSounds(surfaceInfo, true);
                    }
                }
            }

            if (rightHeight > thresholdHeight && !hasRaisedRightFoot)
            {
                hasRaisedRightFoot = true;
            }
            else if (isCrouched && rightHeight > (thresholdHeight + crouchedThresholdAdjustment) && !hasRaisedRightFoot)
            {
                hasRaisedRightFoot = true;
            }
            else if (rightHeight < distanceWhenGrounded && hasRaisedRightFoot)
            {
                hasRaisedRightFoot = false;

                if (rightFootDirection < 0)
                {
                    if (currentAnimatorVelocity > walkLimit)
                    {
                        footstepTriggered = true;
                        FootstepSurfaceInfo surfaceInfo = CheckCurrentSurface(rightFootPosition);
                        TriggerMovementSounds(surfaceInfo, false);
                    }
                    else if (isCrouched && currentAnimatorVelocity >= (walkLimit + crouchedWalkAdjustment))
                    {
                        footstepTriggered = true;
                        FootstepSurfaceInfo surfaceInfo = CheckCurrentSurface(rightFootPosition);
                        TriggerMovementSounds(surfaceInfo, false);
                    }
                }
            }

            previousLeftFootDirection  = leftFootDirection;
            previousRightFootDirection = rightFootDirection;

            previousLeftFootHeight  = leftHeight;
            previousRightFootHeight = rightHeight;

            if (footstepTriggered)
            {
                return;
            }

            // SIDLE:
            // Animator velocity threshold for the character to be considered to be moving is adjustable.
            // <- The character needs to have stopped before the siddle sfx can be triggered again.
            // <- In addition, there is a cooldown period before the siddle sfx can be triggered again.
            //    <- This is because momentary hovering around the threshold value can lead to 'machine gun' -triggering of the sfx.

            // Since the sidle triggering is not foot-specific, as a compromise we will use the surface and position data of the left foot here.
            // <- Should not matter too much, unless the character is very large, in which case splitting the feet siddling sounds to foot-specific
            //    events could come into consideration.

            if (currentAnimatorVelocity > movingThresholdVelocity && !isMoving && !sidleCooldownInProgress)
            {
                FootstepSurfaceInfo surfaceInfo = CheckCurrentSurface(leftFootPosition);

                if (isCrouched)
                {
                    if (foleyPosition != null)
                    {
                        PlayFoley(MovementType.SidleCrouched, foleyPosition);
                    }

                    PlayFootstep(MovementType.SidleCrouched, surfaceInfo.surfaceType, leftFootPosition);
                    PlayLayer(MovementType.SidleCrouched, surfaceInfo.layerType, leftFootPosition);
                }
                else
                {
                    if (foleyPosition != null)
                    {
                        PlayFoley(MovementType.Sidle, foleyPosition);
                    }

                    PlayFootstep(MovementType.Sidle, surfaceInfo.surfaceType, leftFootPosition);
                    PlayLayer(MovementType.Sidle, surfaceInfo.layerType, leftFootPosition);
                }

                isMoving = true;
                sidleCooldownInProgress = true;
                StartCoroutine(Cooldown(sidleCooldownDuration));
            }
            else if (currentAnimatorVelocity < movingThresholdVelocity && isMoving)
            {
                isMoving = false;
            }
        }