Files
XRLib/Assets/Scripts/UVC/Extention/RectTransformEx.cs
2025-06-10 01:09:36 +09:00

195 lines
7.6 KiB
C#

using UnityEngine;
namespace UVC.Extension
{
/// <summary>
/// RectTransform에 대한 유용한 확장 메서드를 제공하는 클래스입니다.
/// </summary>
public static class RectTransformEx
{
/// <summary>
/// RectTransform의 마진을 설정합니다. 부모 요소의 전체 영역을 기준으로 상하좌우 여백을 지정합니다.
/// 앵커는 자동으로 모서리에 설정됩니다(anchorMin=[0,0], anchorMax=[1,1]).
/// </summary>
/// <param name="trans">대상 RectTransform</param>
/// <param name="left">왼쪽 여백</param>
/// <param name="right">오른쪽 여백</param>
/// <param name="top">위쪽 여백</param>
/// <param name="bottom">아래쪽 여백</param>
/// <example>
/// <code>
/// // 게임 오브젝트의 RectTransform에 여백 적용
/// RectTransform panelRect = panel.GetComponent<RectTransform>();
/// panelRect.SetRectMargin(10f, 10f, 10f, 10f); // 사방 10픽셀 여백 설정
///
/// // UI 요소를 부모 컨테이너에 맞추되 여백 주기
/// RectTransform childRect = childObject.GetComponent<RectTransform>();
/// childRect.SetRectMargin(5f, 5f, 20f, 5f); // 상단에 더 큰 여백 설정
/// </code>
/// </example>
public static void SetRectMargin(this RectTransform trans, float left, float right, float top, float bottom)
{
trans.anchorMin = new Vector2(0, 0);
trans.anchorMax = new Vector2(1f, 1f);
trans.offsetMin = new Vector2(left, bottom);
trans.offsetMax = new Vector2(-right, -top);
}
/// <summary>
/// RectTransform의 너비를 설정합니다.
/// </summary>
/// <param name="trans">대상 RectTransform</param>
/// <param name="width">설정할 너비</param>
/// <example>
/// <code>
/// // 버튼의 너비를 200으로 설정
/// RectTransform buttonRect = button.GetComponent<RectTransform>();
/// buttonRect.SetWidth(200f);
/// </code>
/// </example>
public static void SetWidth(this RectTransform trans, float width)
{
trans.SetSizeWithCurrentAnchors(RectTransform.Axis.Horizontal, width);
}
/// <summary>
/// RectTransform의 높이를 설정합니다.
/// </summary>
/// <param name="trans">대상 RectTransform</param>
/// <param name="height">설정할 높이</param>
/// <example>
/// <code>
/// // 패널의 높이를 150으로 설정
/// RectTransform panelRect = panel.GetComponent<RectTransform>();
/// panelRect.SetHeight(150f);
/// </code>
/// </example>
public static void SetHeight(this RectTransform trans, float height)
{
trans.SetSizeWithCurrentAnchors(RectTransform.Axis.Vertical, height);
}
/// <summary>
/// RectTransform의 크기를 설정합니다.
/// </summary>
/// <param name="trans">대상 RectTransform</param>
/// <param name="size">설정할 크기 (너비, 높이)</param>
/// <example>
/// <code>
/// // 이미지의 크기를 100x100으로 설정
/// RectTransform imageRect = image.GetComponent<RectTransform>();
/// imageRect.SetSize(new Vector2(100f, 100f));
/// </code>
/// </example>
public static void SetSize(this RectTransform trans, Vector2 size)
{
trans.SetWidth(size.x);
trans.SetHeight(size.y);
}
/// <summary>
/// RectTransform의 앵커를 중앙에 위치시키고 피벗도 중앙으로 설정합니다.
/// </summary>
/// <param name="trans">대상 RectTransform</param>
/// <example>
/// <code>
/// // 버튼을 화면 중앙에 위치시키기
/// RectTransform buttonRect = button.GetComponent<RectTransform>();
/// buttonRect.SetAnchorsToCenter();
/// buttonRect.anchoredPosition = Vector2.zero; // 중앙 위치에 배치
/// </code>
/// </example>
public static void SetAnchorsToCenter(this RectTransform trans)
{
trans.anchorMin = new Vector2(0.5f, 0.5f);
trans.anchorMax = new Vector2(0.5f, 0.5f);
trans.pivot = new Vector2(0.5f, 0.5f);
}
/// <summary>
/// RectTransform의 앵커와 피벗을 왼쪽 상단으로 설정합니다.
/// </summary>
/// <param name="trans">대상 RectTransform</param>
/// <example>
/// <code>
/// // UI 요소를 왼쪽 상단에 위치시키기
/// RectTransform elementRect = element.GetComponent<RectTransform>();
/// elementRect.SetAnchorsToTopLeft();
/// elementRect.anchoredPosition = new Vector2(10f, -10f); // 약간의 여백 추가
/// </code>
/// </example>
public static void SetAnchorsToTopLeft(this RectTransform trans)
{
trans.anchorMin = new Vector2(0f, 1f);
trans.anchorMax = new Vector2(0f, 1f);
trans.pivot = new Vector2(0f, 1f);
}
/// <summary>
/// RectTransform을 부모 영역에 꽉 차게 설정합니다(마진 없음).
/// </summary>
/// <param name="trans">대상 RectTransform</param>
/// <example>
/// <code>
/// // 배경 이미지를 패널 전체에 채우기
/// RectTransform backgroundRect = backgroundImage.GetComponent<RectTransform>();
/// backgroundRect.StretchToParentEdges();
/// </code>
/// </example>
public static void StretchToParentEdges(this RectTransform trans)
{
trans.SetRectMargin(0f, 0f, 0f, 0f);
}
/// <summary>
/// RectTransform의 위치를 부모 RectTransform 내의 상대 위치(0~1)로 설정합니다.
/// </summary>
/// <param name="trans">대상 RectTransform</param>
/// <param name="normalizedPosition">정규화된 위치 (0,0=왼쪽 하단, 1,1=오른쪽 상단)</param>
/// <example>
/// <code>
/// // 요소를 부모의 오른쪽 상단에 배치
/// RectTransform elementRect = element.GetComponent<RectTransform>();
/// elementRect.SetNormalizedPosition(new Vector2(0.95f, 0.95f));
/// </code>
/// </example>
public static void SetNormalizedPosition(this RectTransform trans, Vector2 normalizedPosition)
{
if (trans.parent is RectTransform parent)
{
trans.anchorMin = trans.anchorMax = new Vector2(0, 0);
trans.pivot = new Vector2(0.5f, 0.5f);
Rect parentRect = parent.rect;
float x = parentRect.x + parentRect.width * normalizedPosition.x;
float y = parentRect.y + parentRect.height * normalizedPosition.y;
trans.anchoredPosition = new Vector2(x, y);
}
}
/// <summary>
/// RectTransform의 사각형 정보를 월드 좌표로 반환합니다.
/// </summary>
/// <param name="trans">대상 RectTransform</param>
/// <returns>월드 좌표계의 사각형 경계</returns>
/// <example>
/// <code>
/// // UI 요소가 특정 월드 좌표를 포함하는지 확인
/// RectTransform elementRect = element.GetComponent<RectTransform>();
/// Rect worldRect = elementRect.GetWorldRect();
/// Vector3 worldPos = Camera.main.ScreenToWorldPoint(Input.mousePosition);
/// bool isOverUI = worldRect.Contains(new Vector2(worldPos.x, worldPos.y));
/// </code>
/// </example>
public static Rect GetWorldRect(this RectTransform trans)
{
Vector3[] corners = new Vector3[4];
trans.GetWorldCorners(corners);
Vector2 min = corners[0];
Vector2 max = corners[2];
return new Rect(min, max - min);
}
}
}