using UnityEngine;
namespace TKS
{
/// 전장 가장자리 벽 표식. 캐스트 질의에서 벽으로 판정한다.
public class BoardWall : MonoBehaviour
{
}
/// 전장(바닥 = 원화 배경 또는 도형·격자 · 테두리 · 4면 벽 콜라이더). 화면보다 넓어 카메라로 스크롤한다.
public class Board : MonoBehaviour
{
public Vector2 Size { get; private set; }
/// Resources/Board/<boardArt> 원화 배경을 썼는가(없으면 도형·격자).
public bool HasArt { get; private set; }
public Rect Rect
{
get { return new Rect(-Size.x * 0.5f, -Size.y * 0.5f, Size.x, Size.y); }
}
public void Build(Vector2 size, string boardArt = null)
{
Size = size;
float w = size.x;
float h = size.y;
Sprite art = string.IsNullOrEmpty(boardArt) ? null : Resources.Load("Board/" + boardArt);
HasArt = art != null;
if (HasArt)
{
// 원화 세션 납품 배경(5:8 · 위 = 적 진영) — 전장 크기에 맞춰 늘린다 · 격자·진영 띠는 그리지 않음
var bg = ProceduralSprites.NewSprite(transform, "Background", art, Color.white, 1f, -20);
bg.transform.localScale = new Vector3(w / art.bounds.size.x, h / art.bounds.size.y, 1f);
}
else
{
var bg = ProceduralSprites.NewSprite(transform, "Background", ProceduralSprites.Square, new Color(0.17f, 0.24f, 0.17f), 1f, -20);
bg.transform.localScale = new Vector3(w, h, 1f);
// 아군·적군 진영 구분용 옅은 띠
var enemyHalf = ProceduralSprites.NewSprite(transform, "EnemyHalf", ProceduralSprites.Square, new Color(0.45f, 0.2f, 0.2f, 0.18f), 1f, -19);
enemyHalf.transform.localScale = new Vector3(w, h * 0.5f, 1f);
enemyHalf.transform.localPosition = new Vector3(0f, h * 0.25f, 0f);
// 격자(4 단위) — 스크롤 체감용
var gridColor = new Color(1f, 1f, 1f, 0.07f);
const float gridStep = 4f;
for (float x = -w * 0.5f + gridStep; x < w * 0.5f - 0.01f; x += gridStep)
{
var g = ProceduralSprites.NewSprite(transform, "GridV", ProceduralSprites.Square, gridColor, 1f, -18);
g.transform.localPosition = new Vector3(x, 0f, 0f);
g.transform.localScale = new Vector3(0.04f, h, 1f);
}
for (float y = -h * 0.5f + gridStep; y < h * 0.5f - 0.01f; y += gridStep)
{
var g = ProceduralSprites.NewSprite(transform, "GridH", ProceduralSprites.Square, gridColor, 1f, -18);
g.transform.localPosition = new Vector3(0f, y, 0f);
g.transform.localScale = new Vector3(w, 0.04f, 1f);
}
var mid = ProceduralSprites.NewSprite(transform, "MidLine", ProceduralSprites.Square, new Color(1f, 1f, 1f, 0.14f), 1f, -17);
mid.transform.localScale = new Vector3(w, 0.06f, 1f);
}
// 테두리
var borderColor = new Color(0.85f, 0.75f, 0.45f);
const float t = 0.16f;
MakeBorder("BorderTop", new Vector2(0f, h * 0.5f + t * 0.5f), new Vector2(w + t * 2f, t), borderColor);
MakeBorder("BorderBottom", new Vector2(0f, -h * 0.5f - t * 0.5f), new Vector2(w + t * 2f, t), borderColor);
MakeBorder("BorderLeft", new Vector2(-w * 0.5f - t * 0.5f, 0f), new Vector2(t, h), borderColor);
MakeBorder("BorderRight", new Vector2(w * 0.5f + t * 0.5f, 0f), new Vector2(t, h), borderColor);
// 벽 콜라이더 (바깥쪽 1 단위 두께)
const float wallT = 1f;
MakeWall("WallTop", new Vector2(0f, h * 0.5f + wallT * 0.5f), new Vector2(w + wallT * 2f, wallT));
MakeWall("WallBottom", new Vector2(0f, -h * 0.5f - wallT * 0.5f), new Vector2(w + wallT * 2f, wallT));
MakeWall("WallLeft", new Vector2(-w * 0.5f - wallT * 0.5f, 0f), new Vector2(wallT, h));
MakeWall("WallRight", new Vector2(w * 0.5f + wallT * 0.5f, 0f), new Vector2(wallT, h));
}
void MakeBorder(string name, Vector2 pos, Vector2 size, Color color)
{
var sr = ProceduralSprites.NewSprite(transform, name, ProceduralSprites.Square, color, 1f, -16);
sr.transform.localPosition = pos;
sr.transform.localScale = new Vector3(size.x, size.y, 1f);
}
void MakeWall(string name, Vector2 pos, Vector2 size)
{
var go = new GameObject(name);
go.transform.SetParent(transform, false);
go.transform.localPosition = pos;
var col = go.AddComponent();
col.size = size;
go.AddComponent();
}
public Vector2 ClampInside(Vector2 p, float radius)
{
var r = Rect;
float x = Mathf.Clamp(p.x, r.xMin + radius, r.xMax - radius);
float y = Mathf.Clamp(p.y, r.yMin + radius, r.yMax - radius);
return new Vector2(x, y);
}
}
}