Files
beyond/Assets/Scripts/InvectorDerivatives/bSpriteHealth.cs
2024-11-20 15:21:28 +01:00

189 lines
5.2 KiB
C#

using Invector;
using Invector.vCharacterController;
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
namespace Beyond
{
public class bSpriteHealth : MonoBehaviour
{
public vHealthController healthControl;
public Camera specificCamera;
[Tooltip("UI to show on receive damage")]
[SerializeField]
protected GameObject healthBar;
public bool lookToCamera = true;
[Header("UI properties")]
[SerializeField] protected Slider _healthSlider;
[SerializeField] protected Slider _damageDelay;
//this is weird
[SerializeField] protected float timeToHideDamageDelay;
[SerializeField] protected float _smoothRegenDelay;
[SerializeField] protected Text _damageCounter;
[SerializeField] protected float _damageCounterTimer = 1.5f;
[SerializeField] protected float _regenTimeCounter = 1.5f;
[SerializeField] protected bool _showDamageType = true;
private bool inDelay;
private float damage;
private float currentSmoothDamage;
public Transform cameraMain;
private bool isForced;
public float damageDelaySpeed = 1f;
public Transform healthCanvas;
// Start is called before the first frame update
private void Start()
{
if (specificCamera)
{
cameraMain = specificCamera.transform;
}
else
{
cameraMain = Camera.main ? Camera.main.transform : null;
}
healthControl.onReceiveDamage.AddListener(Damage);
_healthSlider.maxValue = healthControl.maxHealth;
_healthSlider.value = healthControl.currentHealth;
_damageDelay.maxValue = healthControl.maxHealth;
_damageDelay.value = healthControl.currentHealth;
_damageCounter.text = string.Empty;
if (healthBar) healthBar.SetActive(false);
}
private void OnEnable()
{
_damageDelay.value = _healthSlider.value;
damage = 0;
_damageCounter.text = string.Empty;
inDelay = false;
}
private void SpriteBehaviour()
{
if (lookToCamera && cameraMain != null)
{
// transform.LookAt(cameraMain.position, Vector3.up);
healthCanvas.LookAt(cameraMain.position, Vector3.up);
}
if (healthControl == null || healthControl.currentHealth <= 0)
Destroy(gameObject);
_healthSlider.value = healthControl.currentHealth;
}
private void Update()
{
if (!healthBar && !isForced)
{
SpriteBehaviour();
}
}
public void Damage(vDamage damage)
{
try
{
this.damage += damage.damageValue;
_damageCounter.text = this.damage.ToString("00") + ((_showDamageType && !string.IsNullOrEmpty(damage.damageType)) ? (" : by " + damage.damageType) : "");
_healthSlider.value -= damage.damageValue;
if (!inDelay && healthControl && gameObject.activeInHierarchy)
StartCoroutine(DamageDelay());
}
catch
{
Destroy(this);
}
}
public void ForceShowHpBar()
{
if (healthBar)
{
isForced = true;
healthBar.SetActive(true);
}
}
public void ForceHideHpBar()
{
if (healthBar)
{
healthBar.SetActive(false);
isForced = false;
}
}
public void StartHealthRegen()
{
StartCoroutine(HealthDelay());
}
private IEnumerator HealthDelay()
{
inDelay = true;
ForceShowHpBar();
while (_healthSlider.value < _healthSlider.maxValue)
{
_healthSlider.value += _smoothRegenDelay;
yield return null;
}
inDelay = false;
yield return new WaitForSeconds(_regenTimeCounter);
if (healthBar)
{
ForceHideHpBar();
}
}
private IEnumerator DamageDelay()
{
inDelay = true;
if (healthBar)
{
SpriteBehaviour();
}
if (healthBar)
{
healthBar.SetActive(true);
}
yield return new WaitForSeconds(timeToHideDamageDelay);
while (_damageDelay.value > _healthSlider.value)
{
if (healthBar)
{
SpriteBehaviour();
}
_damageDelay.value -= damageDelaySpeed * Time.deltaTime;
yield return null;
}
inDelay = false;
yield return new WaitForSeconds(_damageCounterTimer);
damage = 0;
_damageCounter.text = string.Empty;
if (healthBar && !isForced)
{
healthBar.SetActive(false);
}
}
}
}