게임에서 퀘스트는 방향성을 제공해 주고 게임의 목적성과 재미를 높여주며, 진행 상황을 추적하고 보상을 제공하여 게임을 보다 흥미롭게 만들어줍니다. 퀘스트 시스템을 구현하고 정리하였습니다.
💬 서론
- 본 글은 게임을 모두 만든 후에 작성한 글로 핵심 주제 외 클래스 및 다른 기능에 대한 함수가 포함될 수 있습니다.
📖 구현 내용
- 적 처치, 아이템 습득에 대한 퀘스트를 구현합니다.
- 플레이어는 퀘스트를 받고 퀘스트를 완료할 수 있습니다.
- 퀘스트 상태를 확인하여 상태별로 이벤트를 처리할 수 있습니다.
- 스크립터블 오브젝트로 퀘스트의 데이터를 관리합니다.
- 스크립터블 오브젝트를 프로젝트 폴더 내에서 관리하고, 이 데이터를 자동으로 불러옵니다.
- ID를 이용하여 고유한 퀘스트의 중복 여부를 검사할 수 있습니다.
- 하나의 퀘스트에서 여러 개의 목표 중 하나만 수행해도 퀘스트를 완료하는지에 대한 여부를 설정할 수 있습니다.
- 퀘스트 콘텐츠를 보여주고 현재 진행 시점, 완료한 퀘스트들의 정보를 볼 수 있습니다.
⚒️ 구현
- 이번 글에서는 퀘스트 콘텐츠 매니저를 사용할 때 풀 사이즈 UI창을 구현하고 구성요소 중 하나인 QuestFullContent 프리팹에대해 다루겠습니다.
· FullContent
더보기
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
using TMPro;
using UnityEngine.SceneManagement;
namespace Quest
{
public class QuestFullContent : QuestCompactContent
{
[SerializeField] private Toggle? mCompactContentToggle;
[SerializeField] private Button? mNaviButton;
public override void UpdateCompactQuestContents(QuestContentData contentData)
{
base.UpdateCompactQuestContents(contentData);
}
public void CompleteQuest()
{
Destroy(mCompactContentToggle.gameObject);
Destroy(mNaviButton.gameObject);
NaviManager.Instance.TryStopNavi(mQuestData.name);
}
public void TOGGLE_CompactContent()
{
QuestContentManager.Instance.ToggleCompactQuestContent(mQuestData, mCompactContentToggle.isOn);
}
public void BTN_DisplayCurrentQuest()
{
QuestContentManager.Instance.ToggleFullQuestContent(mQuestData);
}
public void BTN_Navi()
{
Debug.Log(QuestManager.Instance.CheckQuestState(base.mQuestData.questId));
if(SceneManager.GetActiveScene().name != base.mQuestData.questScene)
return;
if(mQuestData.name == NaviManager.Instance.NaviKeyName)
{
NaviManager.Instance.TryStopNavi(mQuestData.name);
return;
}
switch(QuestManager.Instance.CheckQuestState(base.mQuestData.questId))
{
case QuestState.CLEAR:
{
NaviManager.Instance.StartNavi(mQuestData.name, GameManager.Instance.Player.transform, base.mQuestData.sourcePos);
break;
}
case QuestState.ONGOING:
{
NaviManager.Instance.StartNavi(mQuestData.name, GameManager.Instance.Player.transform, base.mQuestData.destinationPos);
break;
}
}
}
}
}
[SerializeField] private Toggle? mCompactContentToggle;
[SerializeField] private Button? mNaviButton;
- 슬롯 프리팹 내부에 존재하는 토글과 버튼입니다.
- 특정 함수에 의해 이 버튼들이 파괴될 수 있기에 nullable로 설정합니다.
public override void UpdateCompactQuestContents(QuestContentData contentData)
{
base.UpdateCompactQuestContents(contentData);
}
- 부모의 함수를 오버라이드하여 새롭게 정의합니다.
- 풀사이즈UI는 내부에 특별히 업데이트를 할 콘텐츠가 없기에 컴팩트 UI에서 사용하는 텍스트를 사용하도록 요청합니다.
public void CompleteQuest()
{
Destroy(mCompactContentToggle.gameObject);
Destroy(mNaviButton.gameObject);
NaviManager.Instance.TryStopNavi(mQuestData.name);
}
- 퀘스트를 완료한경우 이 슬롯에도 함수가 호출되어 슬롯 내부의 컴팩트 UI표시 토글과 내비게이션 버튼을 파괴합니다.
- 만약 이 퀘스트에 대한 내비게이션이 켜져있다면, 더 이상 필요하지 않으므로 내비게이션을 종료합니다.
- 내비게이션에 대한 내용은 "[유니티] NavMesh를 응용하여 '내비게이션(경로 시각화)' 만들기"에서 확인할 수 있습니다.
public void TOGGLE_CompactContent()
{
QuestContentManager.Instance.ToggleCompactQuestContent(mQuestData, mCompactContentToggle.isOn);
}
public void BTN_DisplayCurrentQuest()
{
QuestContentManager.Instance.ToggleFullQuestContent(mQuestData);
}
- UI에서 입력을 받아 호출되는 함수입니다.
public void BTN_Navi()
{
Debug.Log(QuestManager.Instance.CheckQuestState(base.mQuestData.questId));
if(SceneManager.GetActiveScene().name != base.mQuestData.questScene)
return;
if(mQuestData.name == NaviManager.Instance.NaviKeyName)
{
NaviManager.Instance.TryStopNavi(mQuestData.name);
return;
}
switch(QuestManager.Instance.CheckQuestState(base.mQuestData.questId))
{
case QuestState.CLEAR:
{
NaviManager.Instance.StartNavi(mQuestData.name, GameManager.Instance.Player.transform, base.mQuestData.sourcePos);
break;
}
case QuestState.ONGOING:
{
NaviManager.Instance.StartNavi(mQuestData.name, GameManager.Instance.Player.transform, base.mQuestData.destinationPos);
break;
}
}
}
- 내비게이션을 활성화합니다.
- 이미 동일한 퀘스트에 대한 내비게이션이 활성화되어있다면, 내비게이션을 종료합니다.
- 현재 퀘스트 상태를 고려하여 목적지로 향하는 내비게이션인지, 의뢰자 위치에 대한 내비게이션인지 판단하여 표시하도록 합니다.
· UI 설정
- 전체 구성은 다음과 같습니다.
✅ 사용
- "[유니티] 퀘스트 시스템(3) - 콘텐츠 매니저"에서 사용되는 이 프리팹은 콘텐츠 매니저의 mQuestFullPrefab에 할당해야합니다.
'unity game modules' 카테고리의 다른 글
[유니티] Graphics device is null. 오류 해결 (0) | 2024.01.18 |
---|---|
[유니티] 피해 효과 (Damage effect overlay) (0) | 2023.08.28 |
[유니티] 퀘스트 시스템(4) - 컴팩트 UI (0) | 2023.04.11 |
[유니티] 퀘스트 시스템(3) - 콘텐츠 매니저 (0) | 2023.04.11 |
[유니티] 퀘스트 시스템(2) - 퀘스트 매니저 (0) | 2023.04.11 |