scrPlayerDamageManager

mail@pastecode.io avatar
unknown
csharp
3 years ago
5.4 kB
4
Indexable
Never
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class scrPlayerDamageManager : MonoBehaviour
{
    [Header("Components")]
    [SerializeField] private GameObject ragdoll;

    [Header("Variables")]
    public int heartAmount;
    [HideInInspector] public bool canBeDetected = true;
    [HideInInspector]public bool isDead,hasDied = false;
    [SerializeField] private float invincibilityTime;
    [SerializeField] public float damageDuration;
    [SerializeField] private float damageKnockBackStrength;
    [SerializeField] private float deathImpulseStrength = 1000;
    public float timeUntilRestartAfterDied = 1;
    [HideInInspector] public bool canBeDamaged = true; 
    public bool beeingDamaged = false;
    private SpriteRenderer spr;
    bool isFlickering = false;


    [SerializeField] private float hitStopDuration = 0.1f;
    [SerializeField] private float cameraShakeDuration = 0.2f;
    [SerializeField] private float cameraShakeIntensity = 8f;
    [SerializeField] private float hitStopRetimeVelocity;
    [SerializeField] private ParticleSystem damageParticleFX;

    #region Singleton and Awake
    public static scrPlayerDamageManager instance;
    private void Awake()
    {
        heartAmount = ES3.Load("heartAmount", 3);
        instance = this;
        spr = GetComponentInChildren<SpriteRenderer>();
    }
    #endregion

    private void Start()
    {
        CantBeDamaged(1);
    }

    public void TakeDamage(int damageAmount, bool enemyFacingRight)
    {
        if (!isDead && canBeDamaged)
        {
            //Keep track of whats happening.
            beeingDamaged = true;

            //Applyies damage.
            scrPlayerHeartHealthVisual.heartsHealthSystemStatic.Damage(damageAmount);

            //Effects.
            damageParticleFX.Play();
            scrCameraShake.instance.ShakeCamera(cameraShakeIntensity, cameraShakeDuration);
            scrHitStop.instance.HitStop(hitStopDuration);

            //KnockBack.
            Vector2 knockBackAngle = enemyFacingRight ? new Vector2(1, 1) : new Vector2(-1,1);
            knockBackAngle.Normalize();
            GetComponent<Rigidbody2D>().velocity = Vector2.zero;
            GetComponent<Rigidbody2D>().AddForce(knockBackAngle * damageKnockBackStrength * Time.fixedDeltaTime, ForceMode2D.Impulse);

            //Invincibility time and damageDuration.
            StartCoroutine(WaitForHitStopToEnd(damageDuration));
            StartCoroutine(CantBeDamaged(invincibilityTime));

            //Keep track of resting hearts.
            if (GameManager.instance.playerHealth > 0)
            {
                GameManager.instance.playerHealth -= damageAmount;
            }
        }

        if (isDead)
        {
            Die(enemyFacingRight);
            beeingDamaged = false;
            isDead = false;
            hasDied = true;
            GameManager.instance.playerHealth = heartAmount;
        }
    }

    public void Heal(int healAmount)
    {
        scrPlayerHeartHealthVisual.heartsHealthSystemStatic.Heal(healAmount);
        if (GameManager.instance.playerHealth < heartAmount)
        {
            GameManager.instance.playerHealth += healAmount;
        }
        else
        {
            GameManager.instance.playerHealth = heartAmount;
        }
    }

    private void Die(bool impulseRight)
    {
         scrCameraShake.instance.ShakeCamera(cameraShakeIntensity * 2, cameraShakeDuration);

         Instantiate(ragdoll, transform.position + new Vector3(0, 1, 0), transform.rotation);

         scrPlayerRagdollDeath.instance.DeathImpulse(deathImpulseStrength, impulseRight);

         gameObject.SetActive(false);
         this.enabled = false;
    }

    IEnumerator WaitForHitStopToEnd(float duration)
    {
        scrPlayerController2D.instance.cantMove = true;
        yield return new WaitForSecondsRealtime(duration);
        beeingDamaged = false;
        scrPlayerController2D.instance.cantMove = false;
    }

    IEnumerator CantBeDamaged(float duration)
    {
        canBeDamaged = false;
        yield return new WaitForSecondsRealtime(duration);
        canBeDamaged = true;
    }

    IEnumerator flickerAnimation()
    {
        isFlickering = true;
        spr.color = Color.red;
        yield return new WaitForSeconds(0.1f);
        spr.color = Color.white;
        yield return new WaitForSeconds(0.1f);
        isFlickering = false;
    }

    void Update()
    {
        if (!canBeDamaged && !isFlickering && !scrPlayerIai.instance.iaing)
        {
          StartCoroutine(flickerAnimation());
        }

        if (scrPlayerHeartHealthVisual.heartsHealthSystemStatic.settingUp)
        {
            //Always stay the same health.
            if (GameManager.instance.playerHealth != heartAmount)
            {
                scrPlayerHeartHealthVisual.heartsHealthSystemStatic.settingUp = false;
                
                int damageToDeal = heartAmount -= GameManager.instance.playerHealth;
                scrPlayerHeartHealthVisual.heartsHealthSystemStatic.Damage(damageToDeal);
            }
            else
            {
                scrPlayerHeartHealthVisual.heartsHealthSystemStatic.settingUp = false;
            }

        }
    }
}