Files
Ipseity-Demo/Assets/_Content/Scripts/Features/DetectiveBoard/UI/ConnectionLine.cs
T

171 lines
5.6 KiB
C#

using UnityEngine;
using UnityEngine.UI;
namespace Unheimlich.Features.DetectiveBoard.UI
{
public enum LineColorState
{
Green = 0,
Orange = 1,
Red = 2
}
[RequireComponent(typeof(RectTransform))]
public class ConnectionLine : MonoBehaviour
{
[Header("References")]
[SerializeField] private Image _lineImage;
[SerializeField] private Image _outlineImage;
[SerializeField] private RectTransform _rectTransform;
private RectTransform _lineRectTransform;
private RectTransform _outlineRectTransform;
[Header("Settings")]
[SerializeField] private float _lineThickness = 3f;
[SerializeField] private Color _outlineColor = Color.yellow;
[Header("Color States")]
[SerializeField] private Color _greenColor = Color.green;
[SerializeField] private Color _orangeColor = new Color(1f, 0.5f, 0f);
[SerializeField] private Color _redColor = Color.red;
private PostItNode _startNode;
private PostItNode _endNode;
private LineColorState _colorState = LineColorState.Green;
private bool _isHovered;
public PostItNode StartNode => _startNode;
public PostItNode EndNode => _endNode;
public LineColorState ColorState => _colorState;
private void Awake()
{
if (_rectTransform == null)
_rectTransform = GetComponent<RectTransform>();
if (_lineImage == null)
_lineImage = GetComponentInChildren<Image>();
if (_lineImage != null)
{
_lineRectTransform = _lineImage.GetComponent<RectTransform>();
_lineImage.raycastTarget = true;
}
if (_rectTransform != null)
{
_rectTransform.anchorMin = new Vector2(0.5f, 0.5f);
_rectTransform.anchorMax = new Vector2(0.5f, 0.5f);
_rectTransform.pivot = new Vector2(0f, 0.5f);
}
if (_lineRectTransform != null)
{
_lineRectTransform.anchorMin = new Vector2(0f, 0.5f);
_lineRectTransform.anchorMax = new Vector2(0f, 0.5f);
_lineRectTransform.pivot = new Vector2(0f, 0.5f);
}
if (_outlineImage == null)
{
_outlineImage = transform.Find("Outline")?.GetComponent<Image>();
}
if (_outlineImage != null)
{
_outlineRectTransform = _outlineImage.GetComponent<RectTransform>();
if (_outlineRectTransform != null)
{
_outlineRectTransform.anchorMin = new Vector2(0f, 0.5f);
_outlineRectTransform.anchorMax = new Vector2(0f, 0.5f);
_outlineRectTransform.pivot = new Vector2(0f, 0.5f);
}
_outlineImage.raycastTarget = false;
_outlineImage.gameObject.SetActive(false);
}
}
public void Initialize(PostItNode startNode, PostItNode endNode)
{
_startNode = startNode;
_endNode = endNode;
_colorState = LineColorState.Green;
UpdateColorState();
UpdateLine();
}
public void UpdateLine()
{
if (_startNode == null || _endNode == null || _rectTransform == null)
return;
Vector2 startPos = _startNode.ConnectionPoint.anchoredPosition;
Vector2 endPos = _endNode.ConnectionPoint.anchoredPosition;
Vector2 direction = endPos - startPos;
float distance = direction.magnitude;
_rectTransform.anchoredPosition = startPos;
float angle = Mathf.Atan2(direction.y, direction.x) * Mathf.Rad2Deg;
_rectTransform.localRotation = Quaternion.Euler(0, 0, angle);
if (_lineRectTransform != null)
{
_lineRectTransform.sizeDelta = new Vector2(distance, _lineThickness);
}
if (_outlineRectTransform != null)
{
_outlineRectTransform.sizeDelta = new Vector2(distance, _lineThickness + 3f);
}
}
public void CycleColorState()
{
_colorState = (LineColorState)(((int)_colorState + 1) % 3);
UpdateColorState();
}
public void SetColorState(LineColorState state)
{
_colorState = state;
UpdateColorState();
}
private void UpdateColorState()
{
if (_lineImage == null)
return;
Color targetColor = _colorState switch
{
LineColorState.Green => _greenColor,
LineColorState.Orange => _orangeColor,
LineColorState.Red => _redColor,
_ => _greenColor
};
_lineImage.color = targetColor;
}
public void SetHovered(bool hovered)
{
_isHovered = hovered;
if (_outlineImage != null)
{
_outlineImage.gameObject.SetActive(hovered);
}
}
public bool ConnectsNodes(PostItNode nodeA, PostItNode nodeB)
{
return (_startNode == nodeA && _endNode == nodeB) ||
(_startNode == nodeB && _endNode == nodeA);
}
}
}