본문 바로가기
개발 (Game)/(2021) Unity RTS 포트폴리오

[Day 2-1] 유닛 선택 및 맵과 유닛의 상호작용 구현

by 진현개발일기 2021. 7. 13.

[2021. 7. 13]

 

이전에 만들어 놓은 HexaGrid 타일 맵을 이용하여 유닛을 선택 후 이동 및 맵과 유닛의 상호 작용을 오전에 구현

하였고. 오후에는 유닛 이동을 최종적으로 마쳤다.  블로그 작성은 매일 밤 작업을 마무리 하고 올리기 때문에

코드는 이전에 오류 되었던 것들이 포함되어있지 않을 수 있다.

 

1. 일단 유닛과 상호작용을 할 때 각각의 타일들이 반응을 해야하므로 타일 전용의 Script를 만들었다.

   World씬이라서 WorldTile이라고 네이밍했다.

 

 

2. Units -> Systems 폴더에는 월드씬 내에 유닛과 관련된 시스템 적인 기능들을 수행하는 스크립트를 모아놓는 곳이고

   그리드 위에 놓여져있는 유닛들을 통제하는 GridUnitSystem.cs와 유닛을 선택할 때 필요한 SelectManager.cs를 

   만들었다. 

   Units -> Objects 폴더에는 이후에 만들어질 유닛들이 부모로 삼을 Units 스크립트를 만들었다.

 

 

타일의 컬라이더는 Trigger로 바꾸고 Layer 또한 Background로 변경하였음.
Physics 세팅 또한 타일끼리는 부딪히지 않도록 설정

 

 

일단 테스트로 타일과 유닛의 충돌 여부를 알기위하여 Tile 스크립트에서 OnTriggerEnter로 유닛과 충돌시

빨간색 색깔의 표면을 SetActive(true)로 시켜줬다.

 

충돌 여부 확인 완료

큐브와 맵이 서로 충돌하였는지는 체크하였고. 이제 남은 일은 유닛을 선택하고 움직이는 것이였다.

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using YJH.World.Unit;
 
namespace YJH.World.SelectManager
{
    public class SelectManager : MonoBehaviour
    {
        public static SelectManager instance;
 
        public static Transform SelectedUnits;
 
        RaycastHit hit;
 
        [Header("▼ player-clickable Layer")]
        [Space(10)]
        public LayerMask interactableLayer = new LayerMask();
 
        #region Unity Methods
 
        private void Awake()
        {
            if (!instance) instance = this;
        }
 
        private void Update()
        {
            HandleUnitMoveMent();
        }
 
        #endregion
 
 
        #region Manager Methods
 
        public void HandleUnitMoveMent()
        {
            if (Input.GetMouseButtonDown(0)) // 왼쪽 클릭
            {
                Ray ray = Camera.main.ScreenPointToRay(Input.mousePosition);
                if (Physics.Raycast(ray, out hit, 200, interactableLayer))
                {
                    if (AddedUnit(hit.transform))
                    {
                        // 클릭할 시 하고싶은거 추가
                    }
                }
                else
                {
                    DeselectUnits();
                }
            }
        }
 
 
        public Units AddedUnit(Transform tf)
        {
            Units unit = tf.GetComponent<Units>();
 
            SelectedUnits = tf;
            return unit; // 유닛은 select 해주면서 unit을 return 해줌으로 위에 Handle함수에서는 if 조건문이 true가 된다
                         // 그러므로 조건문 안에는 추가해주고 싶은 함수를 넣어주면 된다.
                         // [진현, 21.07.13]
        }
 
 
        public void DeselectUnits()
        {
            SelectedUnits = null;
        }
 
        #endregion
 
    }
}
 
 
cs

▲ SelectManager는 이때랑 지금 큰 차이가 없기 때문에 이 글에 올려봤다.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using YJH.World.Tile;
 
namespace YJH.World.Unit
{
    public class Units : MonoBehaviour
    {
        [Space(10)]
        [Header("▼ Stepping-on")]
        [Space(10)]
        public WorldTile CurrentTile;
 
 
        #region UnitStats
        [Space(10)]
        [Header("▼ Stats")]
        [Space(10)]
        public float unitMoveStats = 2f;
       // public float unitMoveStats { get { return unitMoveStats; } set { unitMoveStats = value; } }
        public int MovableNum = 1// 이동 가능 횟수
        #endregion
 
 
        #region Unity Methods
 
        private void OnTriggerEnter(Collider other)
        {
            if(other.gameObject.layer.Equals(6&& other.GetComponent<WorldTile>())
            {
                CurrentTile = other.GetComponent<WorldTile>();
                CurrentTile.CurrentType = TileType.UnitExist;
                CurrentTile.tileOwner = this;
            }
        }
 
        private void OnTriggerExit(Collider other)
        {
            if (other.gameObject.layer.Equals(6&& other.GetComponent<WorldTile>())
            {
                CurrentTile.CurrentType = TileType.Empty;
                CurrentTile.tileOwner = null;
                CurrentTile = null;
            }
        }
 
        #endregion
 
 
        #region YJH Methods
 
        #endregion
 
    }
}
 
cs

▲ Units.cs이다. 다음 글에 공개할 WorldTile.cs에 존재하는 Stat을 OnTrigger 함수에서 조절해준다.

유닛 선택에는 성공하였고 다음 글에는 이를 활용하여 유닛 클릭시 이동 가능 범위가 표기되고 실제로 이동까지 구현한 것을 정리하겠다.

728x90