

오늘의 TIL
엔딩 크레딧 작성
Canvas 아래에 마우스 우클릭 > UI > panel
판넬 컬러는 배경과 같은 색상으로
코루틴
코루틴(Coroutine)은 비동기 프로그래밍과 동시성(concurrency) 처리를 위한 프로그래밍 구조로, 함수나 루틴의 실행을 중단(suspend)하고 필요 시 다시 재개(resume)할 수 있는 특성을 가진다. 코루틴은 일반적인 서브루틴(subroutine)과 달리, 실행 흐름을 협력적으로 제어할 수 있으며, 이를 통해 효율적인 자원 관리와 코드 간결화를 가능하게 한다.
코루틴을 사용하려면 using System.Collections;를 using문에 추가해줘야 한다.
코루틴 함수
yield를 통해 값을 반환하며, 함수 실행이 일시 중단된다.
send()로 코루틴에 값을 전달할 수 있다.
next()로 코루틴을 최초로 시작해야 한다
미니프로젝트 : 팀원 소개 카드게임 스크립트 추가 내용
스테이지를 추가하고 스테이지를 넘어가게 하기위한 로직을 구글 검색과 ai검색을 이용하여 작성해보았다.
빈 오브젝트를 추가해서 StageSelectManager 로 명명하고 앞으로 스테이지 선택 UI를 관리하도록 설정했다.
전체 스크립트는 다음과 같다.
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
using UnityEngine.SceneManagement;
public class StageSelectManager : MonoBehaviour
{
[System.Serializable]
public struct StageButton
{
public Button button;
public int stageNumber;
}
public StageButton[] stageButtons;
void Start()
{
RefreshButtonState();
}
public void RefreshButtonState()
{
foreach (var sb in stageButtons)
{
bool unlocked = (sb.stageNumber == 1)
|| PlayerPrefs.GetInt("StageUnlocked_" + (sb.stageNumber - 1), 0) == 1;
// 보이기/숨기기
sb.button.gameObject.SetActive(unlocked);
sb.button.interactable = unlocked;
if (unlocked)
{
// 클릭 리스너 등록 (중복 방지)
sb.button.onClick.RemoveAllListeners();
sb.button.onClick.AddListener(() => LoadStage(sb.stageNumber));
}
}
}
public void LoadStage(int stageNumber)
{
Time.timeScale = 1f;
GameManager.instance.currentStageIndex = stageNumber - 1;
SceneManager.LoadScene("MainScene" + stageNumber);
}
}
순차적으로 스크립트를 분석하면 다음과 같다.
[System.Serializable]
public struct StageButton
{
public Button button;
public int stageNumber;
}
위 함수안에 있는 Button button은 실제 UI에서 클릭할수 있는 버튼 오브젝트이다.
int stageNumber 이 버튼이 나타내는 스테이지 번호
[System.Serializable] 덕분에 이 구조체는 Unity 인스펙터에서 배열로 보이고 버튼과 번호를 에디터에서 직접 할당할수 있다고 한다.(처음 써보는거라 좀더 알아봐야 할거 같다.)
public StageButton[] stageButtons;
// 여러개의 StageButton을 인스펙터에서 할당하여 여러 스테이지 버튼을 한번에 관리하는 배열이다.
void Start()
{
// 씬 시작시 버튼 상태를 초기화한다.
RefreshButtonState();
}
각 버튼의 활성화/비활성화와 클릭 이벤트 등록을 담당한다.
public void RefreshButtonState()
{
foreach (var sb in stageButtons)
{
bool unlocked = (sb.stageNumber == 1)
|| PlayerPrefs.GetInt("StageUnlocked_" + (sb.stageNumber - 1), 0) == 1;
// 보이기/숨기기
sb.button.gameObject.SetActive(unlocked);
sb.button.interactable = unlocked;
if (unlocked)
{
// 클릭 리스너 등록 (중복 방지)
sb.button.onClick.RemoveAllListeners();
sb.button.onClick.AddListener(() => LoadStage(sb.stageNumber));
}
}
}
동작원리
1. 잠금해제 여부 확인
해금이 된 스테이지 버튼에만 클릭 리스너를 등록한다.
기존 리스너는 중복 방지를 위해 모두 제거한다.
클릭시 아래의 LoadStage()를 호출한다.
public void LoadStage(int stageNumber)
{
Time.timeScale = 1f;
GameManager.instance.currentStageIndex = stageNumber - 1;
SceneManager.LoadScene("MainScene" + stageNumber);
}
위 로드스테이지 함수의 주요 역할은 선택한 스테이지로 이동하는 것이다.
동작원리는
그리고 기존의 Retry button 스크립트와 SelectStage 스크립트 등은 ButtonScripts 스크립트에 속해도 괜찮을거 같아서 ButtonScripts 스크립트에 병합하고 이 스크립트를 기존의 리트라이 버튼과 셀렉트 스테이지 스크립트가 들어가던 자리에 삽입해서 작동을 시켜주었다. 정상작동하는것을 확인할 수 있었다.
후기
머릿속에 구상한 진행 방향을 일단 작성해보고 테스트 후 막히는 부분을 구글링과 ai검색등을 이용해서 코드를 짜맞추는 과정이 지난한거 같았다. 대부분은 서치한 코드로 해결이 되었으나, 다음 씬으로 넘어가는 로직을 범용성 있게 쓰기 위해 작성한 코드가 제대로 작동을 하지 않아서 그 부분을 계속해서 수정을 하였으나 결국은 작동이 제대로 되지 않았다. 그래서 고육지책으로 작성한 코드는 주석처리를 하고 단순하게 다음씬으로 바로 로드하게 코드를 작성했더니 그제서야 다음씬으로 넘어가는 버튼이 제대로 작동하였다. 어쩔때는 복잡하게 하는것보다 단순하게 하는게 더 나을때도 있다는 생각이 들었다. 이와 관련된건 나중에 다른 코드들을 강의를 통해 배우고 난 뒤에 적용해봐도 괜찮을거 같다는 다른 팀원의 의견을 듣고 나니 그러면 되겠다 라는 생각이 들었다.
#내일배움캠프 #스파르타내일배움캠프 #스파르타내일배움캠프TIL