개요
대학교에 복학하게 되면서, 수업 과제 겸 프로젝트를 예토전생 시켜 개발을 이어가게 되었습니다. 현재는 프로토타입 개발을 완료한 상황으로, 개발 과정을 복기하면서 글을 적어보고 있습니다.
지난 차례의 글에서 이동 및 차례 처리와 같은 플레이에 필요한 로직들을 대부분 구현했으니, 이제 프로젝트의 핵심 컨셉인 체스 말의 수량을 자유롭게 편집해 덱을 만드는 시스템을 만들 차례입니다.
너무 프로젝트의 볼륨이 커지면 벅찰 것 같다는 생각도 있었고, 프로토타입의 재미 검증이 더 우선이었기 때문에 멀티플레이 구현 없이 (처음엔 데디케이트 서버를 생각만 했었습니다...) 싱글로 오프라인 상에서 게임 플레이를 진행하려 했습니다. 따라서 덱 빌딩 또한 한 화면에서 백이 덱을 구성한 뒤, 흑이 이어서 덱을 구성하는 식으로만 구현했습니다. 😖
덱 빌딩
플레이가 이루어지는 인게임 씬과 분리되도록, 덱 빌딩 씬은 별도의 아웃게임 씬으로 만들었어요. 여기서도 어떤 구조를 만들어야 효율적인 구조가 될 지 조금... 고민했습니다.
그러한 찰나의 고민 끝에, 카드 프리팹에 적용되는 Card 스크립트는 씬 시작 및 덱 빌딩 차례 변경 시 카드의 데이터 세팅 (말 별 이미지·비용·이름 로드, 진영 변경 시 새로고침 등) 만 진행하도록 만들었습니다.
그리고, 카드 및 덱 데이터를 관리하고, 덱 빌딩 차례와 덱 빌딩이 모두 끝났을 경우를 체크해 상태를 변경하고, 게임 씬으로 진입하게 만드는 전반적인 매니저로 기능하게끔 DeckBuildingManager 스크립트를 작성했습니다.
데이터 저장 및 불러오기
덱 빌딩과 인게임 씬으로의 전환하는 부분까지 작업을 완료했으니, 이제 덱빌딩을 통해 만들어진 덱 데이터를 저장하고 게임 씬으로 보내줘야 합니다.
csv, json 같은 형식으로 데이터를 저장해볼까 하다가, 유니티에서 가벼운 로컬 데이터를 저장하고 불러올 때 사용하는 PlayerPrefs 라는 기능을 사용하기로 했습니다. PlayerPrefs 는 Key-Value 방식으로 string 형의 키로 float, int, string 형의 값을 저장합니다. 암호화 없이 로컬 레지스트리에 저장되므로, 민감한 데이터 저장에는 PlayerPrefs를 사용하지 않을 것을 권장하고 있네요.
Unity - Scripting API: PlayerPrefs
Unity stores PlayerPrefs in a local registry, without encryption. Do not use PlayerPrefs data to store sensitive data. Unity stores PlayerPrefs data differently based on which operating system the application runs on. In the file paths given on this page,
docs.unity3d.com
SaveDeckData() 라는 함수로는 DeckBuildingManager 스크립트 상에서 가지는 임시 덱 데이터를 PlayerPrefs로 저장하도록 했어요. 그리고 인게임 씬의 스크립트에서 LoadDeckDataToCardSet() 함수로 PlayerPrefs 에 저장된 데이터를 씬으로 불러오도록 만들었습니다.
// 덱빌딩 씬에서의 덱 데이터 저장
private int[] deckData = new int[5]; // DeckBuildingManager 상에서 들고있는 덱 데이터
···
private void SaveDeckData(Constants.Team team)
{
string temp = team.ToString();
// Save Data on PlayerPrefs
for(int i = 0; i < deckData.Length; ++i)
{
// key = teamEnum_PieceEnum : value
string key = ((int)team).ToString() + "_" + i.ToString();
PlayerPrefs.SetInt(key, deckData[i]);
Debug.Log("Save Deck Data : " + key + " : " + deckData[i]);
}
}
// 게임 씬 상에서의 덱 데이터 불러오기
public void LoadDeckDataToCardSet()
{
string temp = team.ToString();
// Load Data on PlayerPrefs
for(int i = 0; i < 5; ++i)
{
// key = teamEnum_PieceEnum : value
string key = ((int)team).ToString() + "_" + i.ToString();
int count = PlayerPrefs.GetInt(key);
for(int j = 0; j < count; ++j)
{
InstantiateCard((Constants.PieceType) i, team);
}
Debug.Log("Load Deck Data : " + key);
}
// Add King
InstantiateCard(Constants.PieceType.KING, team);
}
가볍게 데이터 저장과 로드를 만들면서, enum 자료형의 진가를 다시금 느끼는 것 같아요. 단순히 int 형으로 설정하고 코드 어딘가에 주석으로 1은 폰, 2는 룩... 과 같이 적어두었었다면 저장하고 로드할 때 게슈탈트 붕괴가 오지 않았을까...
프로젝트를 예토전생해 긴 공백이 있었음에도, 확실히 enum 형의 변수는 보았을 때 직관적으로 데이터를 연상시킬 수 있는 것 같습니다. 그리고, enum 형 값은 string과 int 형으로의 변환이 자유로워, 지지고 볶으며 사용할 수 있으니까요.
다음 포스팅으로 프로젝트MC 개발기는 마무리 지을 것 같습니다. 다음에는 졸업작품으로 만들 프로젝트 개발기를 작성하게 될 것 같은데, 기대 아닌 기대 조금 부탁드리겠습니다! 🥽
'Dev-Log' 카테고리의 다른 글
프로젝트 MC #02 - 말 이동 가능하게 구조 만들기 (0) | 2022.12.18 |
---|---|
프로젝트 MC #01 - 체스 보드 생성하기 (0) | 2022.09.18 |