Unity Input Manager

선비Sunbei·2023년 1월 18일
0

Unity

목록 보기
5/18
post-thumbnail
post-custom-banner

Player의 Input에 대한 반응을 Update() 함수에 몰아서 작성했다.
이는 가독성 면에서 좋지 않다.
따라서 Input Manager를 이용해가지고 극복할 것이다.

Input Manager를 만들기 이전에 설계를 해보자.
1. Manager Script의 Update()를 통해서 Input Manager의 업데이트가 실행된다.
2. Input Manager를 이용하고 싶은 경우, 각 GameObject는 InputManager의 delegagte에 자신의 함수를 등록한다.

// InputManager.cs
using System; // Action을 쓰기 위해서 추가.
using UnityEngine;

public class InputManager
{
    public event Action mAction;

    public void OnUpdate()
    {
        if(mAction != null)
            mAction.Invoke();
    }
}

mAction에서 static을 사용하지않은 이유는 이미 Manager Script에서 유일성이 보장 되기 때문이다. Action은 C#에 기본적으로 정의된 delegate이다.
주의할 점은 MonoBehavoir 상속을 하지않는다는 것이다.
즉, 우리는 InputManager 클래스를 유니티가 관리하는 것이 아닌 일반 클래스로서 사용하려고 한다.
event 키워드를 사용했는데 이는 InputManager에서만 mAction을 호출할 수 있게끔 하기 위해서이다.

// Manager.cs
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class Manager : MonoBehaviour
{

    private static Manager instance = null;
    public static Manager Instance { get {InitManager();return instance;} }
    private static void InitManager()
    { // 생략 }


    private InputManager inputManager = new InputManager();
    public InputManager mInputManager { get { return Instance.inputManager; } }

    void Start()
    {
    }

    void Update()
    {
        mInputManager.OnUpdate();
    }
}

위에서 말했듯이 Manager는 싱글톤패턴에 의해서 유일성이 보장되기 때문에 instance가 유일하다. 따라서 InputManager를 static을 사용해서 선언하지 않았다.

// Player.cs

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class Player : MonoBehaviour
{
    private float mSpeed = 10;

    void Start(){
        Manager.Instance.mInputManager.mAction += OnKeyEvnet;
    }
    void Update()  {}
    void OnKeyEvnet()
    {
        if (Input.GetKey(KeyCode.W))
        {
            transform.rotation = Quaternion.Slerp(transform.rotation, Quaternion.LookRotation(Vector3.forward), 0.2f);
            transform.position += Vector3.forward * Time.deltaTime * mSpeed;
        }
        if (Input.GetKey(KeyCode.S))
        {
            transform.rotation = Quaternion.Slerp(transform.rotation, Quaternion.LookRotation(Vector3.back), 0.2f);
            transform.position += Vector3.back * Time.deltaTime * mSpeed;
        }
        if (Input.GetKey(KeyCode.A))
        {
            transform.rotation = Quaternion.Slerp(transform.rotation, Quaternion.LookRotation(Vector3.left), 0.2f);
            transform.position += Vector3.left * Time.deltaTime * mSpeed;
        }
        if (Input.GetKey(KeyCode.D))
        {
            transform.rotation = Quaternion.Slerp(transform.rotation, Quaternion.LookRotation(Vector3.right), 0.2f);
            transform.position += Vector3.right * Time.deltaTime * mSpeed;
        }
    }
}

Manager를 불러와서 InputManager를 호출, 이벤트에 콜백함수를 등록했다.

post-custom-banner

0개의 댓글