[유니티 코루틴] 유니티 코루틴(Coroutine)


코루틴(Coroutine)이란?

유니티에서 비동기적인 작업을 처리할 때 활용하는 대표적인 기능이 코루틴이다.
Update()와 달리 코루틴은 특정 시간 간격이나 조건에 따라 실행 흐름을 분할 할 수 있어서
반복적인 동작이나 지연 처리가 필요할 때 매우 유용하다.

※ 비동기- 코루틴을 비동기라고 말은 했지만, 스레드 기반 비동기(멀티스레딩)과는 다르다.
메인 스레드 안에서 시분할처럼 실행 되는 형태이다.(협동형 멀티태스킹)

  • 코루틴의 기본 사용 방법

코루틴을 사용하기 위해서는 아래 두가지가 필요하다.

  1. 반환 타입이 IEnumerator 여야 한다.
  2. yield return 구문을 통해 중단점을 지정해야한다.

예제- 코루틴을 이용한 일정 시간 간격으로 적 생성 처리

using System.Collections;
using UnityEngine;

public class EnemySpawner : MonoBehaviour {

    public GameObject enemyPrefab;
    public float spawnInterval = 3f;

    void Start() {
        StartCoroutine(SpawnEnemy());  //코루틴 시작
    }
    
    IEnumerator SpawnEnemy() {
        while (true) {
            Instantiate(enemyPrefab, transform.position, Quaternion.identity);  //적 생성
            yield return new WaitForSeconds(spawnInterval);  //3초 대기
        }
    }
    
}
  • IEnumerator: C#에서 반복자를 나타내는 인터페이스지만, 유니티에서는 Coroutine의 메서드 정의에 활용.
  • yield return:
    – yield return null: 다음 프레임까지 대기 후 이어서 실행
    – yield return new WaitForSeconds(2f): 2초 대기
    – yield return someFunction(): 다른 코루틴이 완료될 때까지 대기

  • StartCoroutine() StopCoroutine()
using System.Collections;
using UnityEngine;

public class EnemySpawner : MonoBehaviour {

    public GameObject enemyPrefab;
    public float spawnInterval = 3f;
    
    public Coroutine spawnCoroutine;  //코루틴 변수

    void Start() {
        spawnCoroutine = StartCoroutine(SpawnEnemy());  //코루틴 시작 및 spawnCoroutine 할당
    }
    
    IEnumerator SpawnEnemy() {
        while (true) {
            Instantiate(enemyPrefab, transform.position, Quaternion.identity);  //적 생성
            yield return new WaitForSeconds(spawnInterval);  //3초 대기
        }
    }
    
    public void OnClick() {
        StopCoroutine(spawnCoroutine);  //실행중인 spawnCoroutine 코루틴 중단
    }
    
}

– StopCoroutine()으로 특정 코루틴을 중단 할 수도 있으며,
– StopAllCoroutines()으로 해당 오브젝트에서 실행 중인 모든 코루틴을 중지 하는 것도 가능하다.


  • 다양한 활용 예시
  • 조건이 충족될 때 까지 대기
bool isCheck = false;

IEnumerator WaitUntilCouroutine() {
    yield return new WaitUntil(() => isCheck);  //isCheck가 true일 때까지 대기
    Debug.Log("isCheck는 true!");
}

  • 네트워크 요청 시 처리
IEnumerator GetDataFromServer(string url) {
    UnityWebRequest request = UnityWebRequest.Get(url);
    yield return request.SendWebRequest();

    if (request.result == UnityWebRequest.Result.Success)
    {
        Debug.Log("요청 성공!: " + request.downloadHandler.text);
    }
    else
    {
        Debug.LogError("요청 실패!: " + request.error);
    }
}


  • 코루틴 사용시 주의 사항
  1. MonoBehaviour에서만 사용 가능
    – StartCoroutine() 및 StopCoroutine()은 MonoBehaviour를 상속받은 클래스에서만 실행 할 수 있다.
  2. 코루틴 중첩 호출 및 While()문 사용 설계
    – 종료 시점을 어떻게 할지 설계 해두는 편이 좋다. yield break; 을 사용하게 되면 해당 코루틴을 종료한다.
  3. 코루틴과 Update() 혼동 주의
    – Update()는 매 프레임마다 호출 되며, 코루틴은 내가 정의한 흐름에 따라 진행하기 때문에,
    적절히 구분해서 사용해야 한다.
  4. 성능 관리
    – 코루틴 자체는 가볍지만, 과도하게 많은 코루틴을 생성하면 오버헤드가 발생할 수 있다.

유니티 코루틴은 게임내에서 대기나 반복이 필요한 로직을 명확하게 구성하는데 도움을 준다.
비동기 흐름의 복잡성을 간단하게 표현해주기 때문에,
프로젝트 규모가 커지더라도 많은 부분에서 유용하게 쓸 수 있다.
기본 사용법 예시만 들었지만, 다음 포스팅에는 코루틴 성능에 대해서 조금 적어 볼 계획이다.

1 thought on “[유니티 코루틴] 유니티 코루틴(Coroutine)”

Leave a Comment