TurnBasedStrategyCourse/Assets/Scripts/Grid/GridSystemVisual.cs

136 lines
5.9 KiB
C#

using System;
using System.Collections.Generic;
using System.Linq;
using Actions;
using UnityEngine;
using UnityEngine.Serialization;
namespace Grid {
public class GridSystemVisual : MonoBehaviour {
public enum GridVisualType {
White,
Red,
Blue,
Yellow,
RedSoft
}
[FormerlySerializedAs("GridSystemVisualSinglePrefab")] [SerializeField]
private Transform gridSystemVisualSinglePrefab;
[FormerlySerializedAs("gridVisualTypeMaterials")] [SerializeField]
private List<GridVisualTypeMaterial> gridVisualTypeMaterialList;
private GridSystemVisualSingle[,] gridSystemVisualSingleArray;
private static GridSystemVisual Instance { get; set; }
private void Awake() {
if (Instance is not null) {
Debug.LogError($"There is more than one GridSystemVisual! {transform} - {Instance}");
Destroy(gameObject);
return;
}
Instance = this;
}
private void Start() {
int width = LevelGrid.Instance.GetWidth();
int height = LevelGrid.Instance.GetHeight();
gridSystemVisualSingleArray = new GridSystemVisualSingle[width, height];
for (int x = 0; x < width; x++) {
for (int z = 0; z < height; z++) {
Transform gridSystemVisualSingleTransform = Instantiate(gridSystemVisualSinglePrefab, LevelGrid.Instance.GetWorldPosition(new(x, z, 0)), Quaternion.identity);
gridSystemVisualSingleArray[x, z] = gridSystemVisualSingleTransform.GetComponent<GridSystemVisualSingle>();
}
}
UnitActionSystem.Instance.OnSelectedActionChanged += UnitActionSystem_OnSelectedActionChanged;
LevelGrid.Instance.OnAnyUnitMovedGridPosition += LevelGrid_OnAnyUnitMovedGridPosition;
UpdateGridVisual();
}
private void LevelGrid_OnAnyUnitMovedGridPosition(object sender, EventArgs e) => UpdateGridVisual();
private void UnitActionSystem_OnSelectedActionChanged(object sender, EventArgs e) => UpdateGridVisual();
private void HideAllGridPosition() {
foreach (GridSystemVisualSingle gridSystemVisualSingle in gridSystemVisualSingleArray)
gridSystemVisualSingle.Hide();
}
private void ShowGridPositionList(List<GridPosition> gridPositionList, GridVisualType gridVisualType) {
foreach (GridPosition gridPosition in gridPositionList)
gridSystemVisualSingleArray[gridPosition.XPosition, gridPosition.ZPosition].Show(GetGridVisualTypeMaterial(gridVisualType));
}
private void ShowGridPositionRange(GridPosition gridPosition, int range, GridVisualType gridVisualType) {
List<GridPosition> gridPositionList = new();
for (int x = -range; x <= range; x++) {
for (int z = -range; z <= range; z++) {
GridPosition testGridPosition = gridPosition + new GridPosition(x, z, 0);
if (!LevelGrid.Instance.IsValidGridPosition(testGridPosition)) continue; //Only return valid grid positions
if (Mathf.Abs(x) + Mathf.Abs(z) > range) continue; //Out of Range
gridPositionList.Add(testGridPosition);
}
}
ShowGridPositionList(gridPositionList, gridVisualType);
}
private void ShowGridPositionRangeSquare(GridPosition gridPosition, int range, GridVisualType gridVisualType) {
List<GridPosition> gridPositionList = new();
for (int x = -range; x <= range; x++) {
for (int z = -range; z <= range; z++) {
GridPosition testGridPosition = gridPosition + new GridPosition(x, z, 0);
if (!LevelGrid.Instance.IsValidGridPosition(testGridPosition)) continue; //Only return valid grid positions
gridPositionList.Add(testGridPosition);
}
}
ShowGridPositionList(gridPositionList, gridVisualType);
}
private void UpdateGridVisual() {
HideAllGridPosition();
BaseAction selectedAction = UnitActionSystem.Instance.SelectedAction;
Unit selectedUnit = UnitActionSystem.Instance.SelectedUnit;
GridVisualType gridVisualType;
switch (selectedAction) {
case SpinAction:
gridVisualType = GridVisualType.Blue;
break;
case GrenadeAction:
gridVisualType = GridVisualType.Yellow;
break;
case ShootAction:
gridVisualType = GridVisualType.Red;
ShowGridPositionRange(selectedUnit.GridPosition, selectedUnit.GetAction<ShootAction>().MaxShootDistance, GridVisualType.RedSoft);
break;
case SwordAction:
gridVisualType = GridVisualType.Red;
ShowGridPositionRangeSquare(selectedUnit.GridPosition, selectedUnit.GetAction<SwordAction>().MaxSwordDistance, GridVisualType.RedSoft);
break;
case InteractAction:
gridVisualType = GridVisualType.Blue;
break;
default:
gridVisualType = GridVisualType.White;
break;
}
ShowGridPositionList(selectedAction.GetValidActionGridPositionList(), gridVisualType);
}
private Material GetGridVisualTypeMaterial(GridVisualType gridVisualType) {
return (from gridVisualTypeMaterial in gridVisualTypeMaterialList where gridVisualTypeMaterial.gridVisualType == gridVisualType select gridVisualTypeMaterial.material).FirstOrDefault();
}
[Serializable]
public struct GridVisualTypeMaterial {
public GridVisualType gridVisualType;
public Material material;
}
}
}