Scriptable Object 

스크립터블 오브젝트(Scriptable Object) 기본 사용법

 

작성 기준 버전 :: 2019.1 ~ 2019.2

 

[이 포스트의 내용은 유튜브 영상으로도 시청하실 수 있습니다]

 

스크립터블 오브젝트(Scriptable Object)는 유니티에서 제공하는 대량의 데이터를 저장하는 데 사용할 수 있는 데이터 컨테이너이다. 스크립터블 오브젝트를 사용하면 값의 사본이 생성되는 것을 방지하여 프로젝트의 메모리 사용을 줄일 수 있으며 이것은 모노비헤이비어(MonoBehaviour) 스크립트에 변경되지 않는 데이터를 저장하는 프리팹을 사용하는 프로젝트에서 유용하다고 한다. 변경되지 않는 데이터를 사용하는 프리팹의 데이터를 일반 변수로 구현할 경우 인스턴스화 할때마다 프리펩에 이 데이터에 대한 자체 사본이 생성되는데, 스크립터블 오브젝트를 사용하면 메모리에 스크립터블 오브젝트의 데이터 사본만을 저장하고 이를 참조하는 방식으로 작동한다고 한다.

 

스크립터블 오브젝트 클래스는 유니티에서 기본적으로 제공하는 것으로 모노비헤이비어 클래스와 마찬가지로 기본 유니티 오브젝트(Unity Object)에서 파생되지만, 모노비헤이비어와 달리, 게임 오브젝트에 컴포넌트로 부착할 수 없고, 프로젝트에 에셋으로 저장된다.

 

 

스크립터블 오브젝트 만들기

 

스크립터블 오브젝트를 만들기 위해서는 ScriptableObject 클래스를 상속받아서 아래의 코드와 같이 구현하면 된다.

 

using UnityEngine;

[CreateAssetMenu(fileName = "Zombie Data", menuName = "Scriptable Object/Zombie Data", order = int.MaxValue)]
public class ZombieData : ScriptableObject
{
    [SerializeField]
    private string zombieName;
    public string ZombieName { get { return zombieName; } }
    [SerializeField]
    private int hp;
    public int Hp { get { return hp; } }
    [SerializeField]
    private int damage;
    public int Damage { get { return damage; } }
    [SerializeField]
    private float sightRange;
    public float SightRange { get { return sightRange; } }
    [SerializeField]
    private float moveSpeed;
    public float MoveSpeed { get { return moveSpeed; } }
}

 

CreateAssetMenu 속성은 스크립터블 오브젝트 스크립트를 이용해서 빠르고 쉽게 에셋을 생성할 수 있게 만들어주는 속성이다.

 

 

 

코드를 빌드하고 에디터로 돌아가서 Assets 메뉴를 보면 추가한 menuName 대로 Create>Scriptable Object>Zombie Data 항목이 새로 생긴 것을 볼 수 있다.

 

 

그리고 그 항목을 선택하면 Zombie Data의 스크립터블 오브젝트가 생성된다.

 

 

생성된 Zombie Data 스크립터블 오브젝트를 선택해보면 위의 이미지와 같이 좀비의 정보에 대한 프로퍼티들이 보인다.

 

 

 

 

 

스크립터블 오브젝트 사용하기

 

앞에서 스크립터블 오브젝트를 생성하는 방법을 배웠으니 이번에는 스크립터블 오브젝트를 사용하는 방법에 대해서 알아보자.

 

 이름 체력 데미지 시야  이동속도 
일반 좀비(Normal Zombie) 10  10 
스피드 좀비(Speed Zombie) 10 
파워 좀비(Power Zombie)  10  10 
탱커 좀비(Tank Zombie)  20  10  1.5 
센서 좀비(Sensor Zombie) 20 

 

위의 표와 같이 다섯 종류의 좀비 데이터를 담을 스크립터블 오브젝트를 만들어보자.

 

 

우선 제일 처음 만든 스크립터블 오브젝트를 복사해서 다섯 개로 만든다.

 

 

각 파일의 이름을 좀비 종류에 맞게 바꿔준다.

 

 

 

그리고 표의 내용에 맞게 각 스크립터블 오브젝트에 데이터를 입력해준다.

 

public class Zombie : MonoBehaviour
{
    [SerializeField]
    private ZombieData zombieData;
    public ZombieData ZombieData { set { zombieData = value; } }

    public void WatchZombieInfo()
    {
        Debug.Log("좀비 이름 :: " + zombieData.ZombieName);
        Debug.Log("좀비 체력 :: " + zombieData.Hp);
        Debug.Log("좀비 공격력 :: " + zombieData.Damage);
        Debug.Log("좀비 시야 :: " + zombieData.SightRange);
        Debug.Log("좀비 이동속도 :: " + zombieData.MoveSpeed);
    }
}

 

그 다음에는 좀비 데이터를 사용할 좀비 클래스를 작성하고

 

 

좀비 클래스를 사용하는 프리팹을 만들어준다.

 

public enum ZombieType 
{
    Normal, Power, Sensor, Speed, Tank 
}

public class ZombieSpawner : MonoBehaviour
{
    [SerializeField]
    private List<ZombieData> zombieDatas;
    [SerializeField]
    private GameObject zombiePrefab;
    
    void Start()
    {
        for (int i = 0; i < zombieDatas.Count; i++)
        {
            var zombie = SpawnZombie((ZombieType)i);
            zombie.WatchZombieInfo();
        }
    }
    
    public Zombie SpawnZombie(ZombieType type)
    {
        var newZombie = Instantiate(zombiePrefab).GetComponent<Zombie>();
        newZombie.ZombieData = zombieDatas[(int)type];
        return newZombie;
    }
}

 

좀비를 소환하는 좀비 스포너 클래스를 만들고 Start() 함수에는 테스트용 코드를 작성한다.

 

 

코드를 작성한 뒤에는 씬에 좀비 스포너 게임 오브젝트를 만들고 거기에 Zombie Spawner 컴포넌트를 붙인 뒤에, 앞에서 만든 좀비 데이터 스크립터블 오브젝트와 좀비 프리팹을 프로퍼티에 넣어준다.

 

 

모든 세팅을 마친 다음에 플레이 버튼을 눌러서 실행해보면 좀비 게임 오브젝트가 생성되고, 콘솔 창에서는 각 좀비의 정보가 출력되는 것을 볼 수 있다.

 

 

그리고 하이어라키 뷰에서 각 좀비의 게임 오브젝트를 살펴보면 각 Zombie 컴포넌트의 Zombie Data 프로퍼티에는 서로 다른 좀비 데이터 스크립터블 오브젝트들이 참조되고 있는 것을 확인할 수 있다.

 

 

 

 

 

스크립터블 오브젝트의 특징 및 응용

 

에디터에서는 스크립터블 오브젝트에 데이터를 저장하는 작업이 언제나 가능하지만, 배포된 빌드에서는 데이터를 저장할 수 없고 개발시 설정한 스크립터블 오브젝트 에셋에 저장된 데이터만을 사용할 수 있다.

 

 

그리고 스크립터블 오브젝트는 에셋 파일 형태로 관리되기 때문에 에셋번들 태그를 이용해서 에셋 번들로 빌드하고 배포하는 방식으로 게임 데이터를 업데이트시키는데 사용할 수도 있다.

 

[유니티 어필리에이트 프로그램]

아래의 링크를 통해 에셋을 구매하시거나 유니티를 구독하시면 수익의 일부가 베르에게 수수료로 지급되어 채널의 운영에 도움이 됩니다.

 

에셋스토어

여러분의 작업에 필요한 베스트 에셋을 찾아보세요. 유니티 에셋스토어가 2D, 3D 모델, SDK, 템플릿, 툴 등 여러분의 콘텐츠 제작에 날개를 달아줄 다양한 에셋을 제공합니다.

assetstore.unity.com

 

Easy 2D, 3D, VR, & AR software for cross-platform development of games and mobile apps. - Unity Store

Have a 2D, 3D, VR, or AR project that needs cross-platform functionality? We can help. Take a look at the easy-to-use Unity Plus real-time dev platform!

store.unity.com

 

Create 2D & 3D Experiences With Unity's Game Engine | Unity Pro - Unity Store

Unity Pro software is a real-time 3D platform for teams who want to design cross-platform, 2D, 3D, VR, AR & mobile experiences with a full suite of advanced tools.

store.unity.com

[투네이션]

 

-

 

toon.at

[Patreon]

 

WER's GAME DEVELOP CHANNEL님이 Game making class videos 창작 중 | Patreon

WER's GAME DEVELOP CHANNEL의 후원자가 되어보세요. 아티스트와 크리에이터를 위한 세계 최대의 멤버십 플랫폼에서 멤버십 전용 콘텐츠와 체험을 즐길 수 있습니다.

www.patreon.com

[디스코드 채널]

 

Join the 베르의 게임 개발 채널 Discord Server!

Check out the 베르의 게임 개발 채널 community on Discord - hang out with 399 other members and enjoy free voice and text chat.

discord.com

 

반응형
  1. 익명 2021.01.04 10:55

    비밀댓글입니다

  2. ?? 2021.07.07 20:06

    잘보았습니다.
    다만 예시가 어울리지 않다고 느끼는건 ScriptableObject 좀비 데이터를 5개 만든다해도 결국 5종의 좀비 밖에 사용못하는 것이므로
    설명에서 말한 것처럼 메모리가 적어지는 것 아닙니다.
    ScriptableObject 데이터가 의미있는 것은 하나의 데이터를 공유하는 경우에만 의미가 있어 보입니다.
    예를 들면 사운드 볼륨같은 것 말입니다.

+ Recent posts