유니티 심화 개인과제 주차 시작 (1-3 ~ 1-5)
오늘 또 새 팀을 배정받았다. 이번엔 다섯명이던데 아 난 이미 6명에 익숙해져 버렸다... 6명이면 내 할일이 줄어들어서 좋았는데 이제는 더 하게 생겼다. 그래 저번주엔 좀 쉽게 했으니까 다시 어려울때가 되긴했지... 오늘은 수준별 실시간 강의에서 배운 내용을 정리해보려 한다.
public class PlayerStats : MonoBehaviour
{
public int hp = 100;
public int mp = 100;
public bool isGodMode = false;
public void IniPlayerData()
{
hp = 100;
mp = 100;
isGodMode = false;
}
}
예를 들어 이렇게 간단하게 플레이어 스탯을 정했다고 가정해보자.

우리가 많이 보던 그 inspector창이다. 하지만 Unity의 Editor 클래스를 상속하여 CustomInspector를 만들면,
이 화면을 완전히 원하는 대로 커스터마이징할 수 있다.
[CustomEditor(typeof(PlayerStats))]
public class PlayerStatsEditor : Editor
{
//인스펙터뷰에 GUI를 커스텀하기 위한 기본 메서드
public override void OnInspectorGUI()
{
var playerStats = (PlayerStats)target;
}
}
CustomEditor(typeof(PlayerStats))는 유니티에게 PlayerStats 클래스를 inspector창에 렌더링할 때 기본 대신 이 PlayerStatsEditor를 호출하라는 의미이다.
OnInspectorGUI()는 메서드를 override하여 실제 보일 GUI를 직접 그리게 된다.
EditorGUILayout.Space();
EditorGUILayout.HelpBox("주인공 캐릭터 스탯", MessageType.Info);
EditorGUILayout.Space();
EditorGUILayout.HelpBox(string message, MessageType type)은 유니티 에디터 내에서 정보박스를 그린다. helpBox외에 Info, Warning, Error 등을 사용할 수도 있다....만 그닥 쓸일은 없을지도?
IntSlider로 수치 조절 //입력 필드
playerStats.hp = EditorGUILayout.IntField("생명", playerStats.hp);
playerStats.mp = EditorGUILayout.IntSlider("마력", playerStats.mp, 0, 100);//슬라이드로. min, max값
IntSlider는 슬라이드로 보일 수 있게 한다. 최소, 최대값을 설정할 수 있다.IntField는 꾸미기 전과 다르지 않지만 이렇게 스크립트로 커스텀하여 제어하기로 한 이상 다 해줘야 한다.
//가로로
EditorGUILayout.BeginHorizontal();
//무적모드 토글 버튼
if(GUILayout.Button(playerStats.isGodMode ? "일반모드로 전환" : "무적모드로 전환"))
{
playerStats.isGodMode = !playerStats.isGodMode;
}
//플레이어 데이터 초기화 버튼
if(GUILayout.Button("데이터 초기화"))
{
playerStats.IniPlayerData();
}
EditorGUILayout.EndHorizontal();
EditorGUILayout.BeginHorizontal() / EditorGUILayout.EndHorizontal()은 이 사이에 그려지는 모든 UI요소를 가로에 배치한다.
이렇게 하면 아래와 같이 된다.

이렇듯 Editor를 상속 받으면 Inspector창에 정보 박스, 슬라이더, 버튼, 가로 레이아웃 등을 자유롭게 조합할 수 있다. 앞으로 프로젝트에서 활용해 보도록 하자!
아이템데이터를 만들때 ScriptableObject를 사용해서 많이 만들었었는데 이것도 조금 다른 방법이 있다고 한다.
public enum ItemType
{
Weapon,
Armor,
Cunsumable
}
public class ItemData : ScriptableObject
{
public string itemName;
public ItemType itemType;
public int quantity;
public bool isMultiple;
}
원래대로라면 여기에 CreateAssetMenu하면서 막 만들었을텐데 그냥 이렇게 끝내고 스크립트를 하나 더 작성해서 거기서 만들어보도록 하겠다.
public class ItemCreator : EditorWindow
{
private string itemName = "New Item";
private ItemType itemType = ItemType.Weapon;
private int quantity = 1;
private bool isMultiple = false;
[MenuItem("Window/Item Creator")]
private static void ShowWindow()//이 메소드를 호출한다
{
GetWindow<ItemCreator>("아이템 생성");
}
private void OnGUI()
{
itemName = EditorGUILayout.TextField("아이템 이름", itemName);
itemType = (ItemType)EditorGUILayout.EnumPopup("아이템 종류", itemType);
quantity = EditorGUILayout.IntField("수량", quantity);
isMultiple = EditorGUILayout.Toggle("복수 보유 여부", isMultiple);
if(GUILayout.Button("아이템 생성"))
{
ItemData data = ScriptableObject.CreateInstance<ItemData>();
data.itemName = itemName;
data.itemType = itemType;
data.quantity = quantity;
data.isMultiple = isMultiple;
//프로젝트 뷰에 에셋 만들기
AssetDatabase.CreateAsset(data, $"Assets/{itemName}.asset");
AssetDatabase.SaveAssets();//이걸 써야 저장이 된다. 이렇게 두 줄로 유니티에 에셋 만들기
}
}
}
EditorWindow를 먼저 상속해준다.ShowWindow() 메서드에 [MenuItem("Window/Item Creator")]를 붙여 Unity 상단 메뉴의 Window → Item Creator로 창을 띄울 수 있다.AssetDatabase.CreateAsset(data, $"Assets/{itemName}.asset")처럼 작성해 정할 수 있다.이렇게 하면 아래와 같이 된다.

원하는 대로 입력 폼을 구성할 수 있어 좋지만 기본으로 주어지는 것도 충분히 좋고 이렇게 하면 코드가 복잡해질 수 있어 취향에 따라 사용하자.
하 역시 튜터님들의 강의는 명강의인것 같다. 그냥 내가 이 튜터님을 좋아하는걸지도 ㅋ 오늘도 새로운 것을 배웠다. 너무너무 유익하다. 이럴때면 여기 신청하길 잘했다고 생각될 정도. 까먹지 않게 최대한 적으려고 했다. 또.. 또 새로운거 알려주셨으면 좋겠다...
내일은 오늘에 이어서 강의를 들을까한다. 빨리 해치우고 개인과제를 시작하고 싶다.