- Simulated "fake" physics and collisions - Object pooling for tiles, obstacles and monster spawns - Base monster scoring with proximity triggers and depth multiplier Co-authored-by: AlexanderT <alexander@foolhardyhorizons.com> Co-authored-by: Michal Pikulski <michal.a.pikulski@gmail.com> Reviewed-on: #5
243 lines
8.0 KiB
C#
243 lines
8.0 KiB
C#
using UnityEngine;
|
|
using System.Collections;
|
|
|
|
namespace Minigames.DivingForPictures
|
|
{
|
|
/// <summary>
|
|
/// Handles visual feedback for player damage by making the sprite renderer blink red.
|
|
/// Automatically subscribes to damage events from PlayerCollisionBehavior components.
|
|
/// </summary>
|
|
public class PlayerBlinkBehavior : MonoBehaviour
|
|
{
|
|
[Header("Blink Settings")]
|
|
[Tooltip("Color to blink to when taking damage (typically red for damage indication)")]
|
|
[SerializeField] private Color damageBlinkColor = Color.red;
|
|
|
|
[Tooltip("How fast to blink between normal and damage colors (seconds between color changes)")]
|
|
[SerializeField] private float blinkRate = 0.15f;
|
|
|
|
[Tooltip("Alpha value for the damage color (0 = transparent, 1 = opaque)")]
|
|
[Range(0f, 1f)]
|
|
[SerializeField] private float damageColorAlpha = 0.7f;
|
|
|
|
[Header("References")]
|
|
[Tooltip("The SpriteRenderer to apply blink effects to (auto-assigned if empty)")]
|
|
[SerializeField] private SpriteRenderer targetSpriteRenderer;
|
|
|
|
private bool _isBlinking;
|
|
private bool _isShowingDamageColor;
|
|
private Coroutine _blinkCoroutine;
|
|
private Color _originalColor; // Missing field declaration
|
|
|
|
private void Awake()
|
|
{
|
|
// Auto-assign sprite renderer if not set
|
|
if (targetSpriteRenderer == null)
|
|
{
|
|
targetSpriteRenderer = GetComponent<SpriteRenderer>();
|
|
if (targetSpriteRenderer == null)
|
|
{
|
|
targetSpriteRenderer = GetComponentInChildren<SpriteRenderer>();
|
|
if (targetSpriteRenderer != null)
|
|
{
|
|
Debug.Log($"[PlayerBlinkBehavior] Found SpriteRenderer on child object: {targetSpriteRenderer.gameObject.name}");
|
|
}
|
|
}
|
|
}
|
|
|
|
if (targetSpriteRenderer == null)
|
|
{
|
|
Debug.LogError("[PlayerBlinkBehavior] No SpriteRenderer found on this GameObject or its children!");
|
|
return;
|
|
}
|
|
|
|
// Store original color
|
|
_originalColor = targetSpriteRenderer.color;
|
|
|
|
// Ensure damage color has the correct alpha
|
|
damageBlinkColor.a = damageColorAlpha;
|
|
}
|
|
|
|
private void OnEnable()
|
|
{
|
|
// Subscribe to immunity events (renamed from damage events)
|
|
PlayerCollisionBehavior.OnImmunityStarted += StartBlinking;
|
|
PlayerCollisionBehavior.OnImmunityEnded += StopBlinking;
|
|
}
|
|
|
|
private void OnDisable()
|
|
{
|
|
// Unsubscribe from immunity events
|
|
PlayerCollisionBehavior.OnImmunityStarted -= StartBlinking;
|
|
PlayerCollisionBehavior.OnImmunityEnded -= StopBlinking;
|
|
|
|
// Stop any ongoing blink effect
|
|
if (_blinkCoroutine != null)
|
|
{
|
|
StopCoroutine(_blinkCoroutine);
|
|
_blinkCoroutine = null;
|
|
}
|
|
|
|
// Restore original color
|
|
RestoreOriginalColor();
|
|
}
|
|
|
|
/// <summary>
|
|
/// Starts the red blinking effect when damage begins
|
|
/// </summary>
|
|
private void StartBlinking()
|
|
{
|
|
if (targetSpriteRenderer == null) return;
|
|
|
|
Debug.Log("[PlayerBlinkBehavior] Starting damage blink effect");
|
|
|
|
// Stop any existing blink coroutine
|
|
if (_blinkCoroutine != null)
|
|
{
|
|
StopCoroutine(_blinkCoroutine);
|
|
}
|
|
|
|
_isBlinking = true;
|
|
_isShowingDamageColor = false;
|
|
|
|
// Start the blink coroutine
|
|
_blinkCoroutine = StartCoroutine(BlinkCoroutine());
|
|
}
|
|
|
|
/// <summary>
|
|
/// Stops the blinking effect when damage ends
|
|
/// </summary>
|
|
private void StopBlinking()
|
|
{
|
|
Debug.Log("[PlayerBlinkBehavior] Stopping damage blink effect");
|
|
|
|
_isBlinking = false;
|
|
|
|
// Stop the blink coroutine
|
|
if (_blinkCoroutine != null)
|
|
{
|
|
StopCoroutine(_blinkCoroutine);
|
|
_blinkCoroutine = null;
|
|
}
|
|
|
|
// Restore original color
|
|
RestoreOriginalColor();
|
|
}
|
|
|
|
/// <summary>
|
|
/// Coroutine that handles the blinking animation
|
|
/// </summary>
|
|
private IEnumerator BlinkCoroutine()
|
|
{
|
|
while (_isBlinking && targetSpriteRenderer != null)
|
|
{
|
|
// Toggle between original and damage colors
|
|
if (_isShowingDamageColor)
|
|
{
|
|
targetSpriteRenderer.color = _originalColor;
|
|
_isShowingDamageColor = false;
|
|
}
|
|
else
|
|
{
|
|
targetSpriteRenderer.color = damageBlinkColor;
|
|
_isShowingDamageColor = true;
|
|
}
|
|
|
|
// Wait for blink interval
|
|
yield return new WaitForSeconds(blinkRate);
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// Restores the sprite renderer to its original color
|
|
/// </summary>
|
|
private void RestoreOriginalColor()
|
|
{
|
|
if (targetSpriteRenderer != null)
|
|
{
|
|
targetSpriteRenderer.color = _originalColor;
|
|
_isShowingDamageColor = false;
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// Updates the original color reference (useful if sprite color changes during gameplay)
|
|
/// </summary>
|
|
public void UpdateOriginalColor()
|
|
{
|
|
if (targetSpriteRenderer != null && !_isBlinking)
|
|
{
|
|
_originalColor = targetSpriteRenderer.color;
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// Public method to change blink color at runtime
|
|
/// </summary>
|
|
public void SetDamageBlinkColor(Color newColor)
|
|
{
|
|
damageBlinkColor = newColor;
|
|
damageBlinkColor.a = damageColorAlpha;
|
|
}
|
|
|
|
/// <summary>
|
|
/// Public method to change blink rate at runtime
|
|
/// </summary>
|
|
public void SetBlinkRate(float rate)
|
|
{
|
|
blinkRate = rate;
|
|
}
|
|
|
|
/// <summary>
|
|
/// Check if currently blinking
|
|
/// </summary>
|
|
public bool IsBlinking => _isBlinking;
|
|
|
|
/// <summary>
|
|
/// Manually trigger blink effect (useful for testing or other damage sources)
|
|
/// </summary>
|
|
public void TriggerBlink(float duration)
|
|
{
|
|
if (_blinkCoroutine != null)
|
|
{
|
|
StopCoroutine(_blinkCoroutine);
|
|
}
|
|
|
|
StartCoroutine(ManualBlinkCoroutine(duration));
|
|
}
|
|
|
|
/// <summary>
|
|
/// Coroutine for manually triggered blink effects
|
|
/// </summary>
|
|
private IEnumerator ManualBlinkCoroutine(float duration)
|
|
{
|
|
_isBlinking = true;
|
|
_isShowingDamageColor = false;
|
|
|
|
float elapsed = 0f;
|
|
|
|
while (elapsed < duration && targetSpriteRenderer != null)
|
|
{
|
|
// Toggle between original and damage colors
|
|
if (_isShowingDamageColor)
|
|
{
|
|
targetSpriteRenderer.color = _originalColor;
|
|
_isShowingDamageColor = false;
|
|
}
|
|
else
|
|
{
|
|
targetSpriteRenderer.color = damageBlinkColor;
|
|
_isShowingDamageColor = true;
|
|
}
|
|
|
|
yield return new WaitForSeconds(blinkRate);
|
|
elapsed += blinkRate;
|
|
}
|
|
|
|
// Ensure we end with original color
|
|
RestoreOriginalColor();
|
|
_isBlinking = false;
|
|
}
|
|
}
|
|
}
|