Unity 6 ) InputSystem

1. 이전 InputSytem과 비교
기존 InputSystem | Unity 6버전 InputSystem |
|---|---|
| 입력이 생기면 정해둔 메서드가 불린다. |
2. Unity 6 에서의 InputSystem
입력의 이름을 담는 값 : 액션마다 값의 형태를 정하며 방향키 넷을 묶어 Vector2 하나로도 받음
이름을 묶는 단위 : Action Map 단위로 묶고, 묶음째 켜고 끔
설정이 있는 곳 : 패키지로 설치하고, 설정은 프로젝트의 에셋 파일로 둠
- 패키지를 설치하지 않으면 Unity는 이전처럼 Input Manager로 동작합니다.
2-1) InputSystem 설정 방법
Project Settings -> Player -> Active Input Handling 설정에서
이전버전 (Input Manager) , 현재버전 (Input System Package) 혹은 둘다 (both) 선택하여 가능합니다.
2-2) Input Actions 에셋

칸 | 담기는 것 |
|---|---|
| 액션을 묶은 단위의 목록 |
| 왼쪽에서 고른 묶음에 들어 있는 액션과, 액션마다 묶인 키 |
| 가운데에서 고른 액션의 설정. 키를 고르면 제목이 |
2-3) Action Map, Action, Binding

단계 | 뜻 | 예 |
|---|---|---|
Action Map | 액션을 묶은 단위. 묶음째 켜고 끕니다 |
|
Action | 게임 안에서 하려는 일의 이름. 스크립트가 아는 것은 이 이름입니다 |
|
Binding | 액션에 실제 키를 묶은 것. 한 액션에 여럿을 묶을 수 있습니다 | W·A·S·D, Space |

- Action Type 을 Value로, Control Type을 Vector2 로 놓게 된다면,
Add Up₩Down₩.... Composite로 한번에 방향키 설정도 가능하다. - 정규화작업이 이미 Composite안에서 이루어져 있어, 따로 정규화작업을 하지 않아도 됩니다.
2-4) PlayerInput

항목 | 정하는 것 |
|---|---|
| 쓸 Input Actions 에셋. 생성한 |
| 재생할 때 켜 둘 Action Map. 적용할 Map을 고릅니다. |
| 액션이 일어났을 때 스크립트에 알리는 방법 |
- Behaviour 설정에 따라 액션 전달 방식이 다르기 때문에 어떤 방식을 채택하는 것이 적절한지 생각해보아야 한다.
Behavior | 알리는 방법 |
|---|---|
| 같은 게임 오브젝트의 스크립트에서 이름이 맞는 메서드를 찾아 부릅니다. |
|
|
| 액션마다 인스펙터에 이벤트 칸이 생기고, 거기 연결한 메서드를 부릅니다. |
| 코드에서 구독하는 C# 이벤트로 알립니다. 인스펙터에서는 연결할 수 없습니다. |
2-4-1) Send Messages, Broadcast Messages 방식
==Behavior==를 ==Send Messages나 Broadcast Messages==로 두면 PlayerInput은 액션 이름 앞에 ==On==을 붙인 이름의 메서드를 찾아 부릅니다.
using UnityEngine;
using UnityEngine.InputSystem;
public class MoveTest : MonoBehaviour
{
[SerializeField] private float _moveSpeed = 5f;
private Vector2 _moveInput;
private void Update()
{
Move();
}
public void OnMove(InputValue value)
{
_moveInput = value.Get<Vector2>();
}
public void OnJump()
{
Debug.Log("MoveTest : Jump 액션이 들어왔습니다.");
}
private void Move()
{
Vector3 direction = new Vector3(_moveInput.x, 0f, _moveInput.y);
transform.Translate(direction * _moveSpeed * Time.deltaTime);
}
}
- OnMove는 InputValue를 받아 액션의 값을 담아 오는 상자이며, Get ()로 꺼냅니다.
- OnJump는 값이 필요 없으므로 아무것도 받지 않습니다.
- 메서드 이름은 On 뒤에 액션 이름을 대문자로 시작해 붙인 형태 그대로여야 불립니다.
액션 이름이 Move인데 메서드를 Onmove나 OnMoving으로 쓰면 불리지 않습니다.
키를 눌러도 반응이 없을 때 먼저 볼 곳이 이 이름입니다. - Send Messages는 Button 액션에서는 누를 때만 메서드를 부르고, Value 액션에서는 값이 바뀔 때마다 부릅니다.
키를 다 떼면 OnMove가 (0, 0)을 받아 불리므로 캡슐이 멈춥니다.
2-4-2) Invoke Unity Events 방식
Behavior를 Invoke Unity Events로 바꾸면 인스펙터에 Events 항목이 생기고,
UnityEvent 칸에 메서드를 연결한 것과 같은 방법으로 연결합니다.
public void OnMove(InputAction.CallbackContext context)
{
_moveInput = context.ReadValue<Vector2>();
}
public void OnJump(InputAction.CallbackContext context)
{
Debug.Log($"PlayerMover: Jump 단계는 {context.phase}입니다.");
}
- 이 상태로 재생하고 Space를 한 번 눌렀다 떼면 Console에 한 줄이 아니라 여러 줄이 찍힙니다.
PlayerMover: Jump 단계는 Started입니다.
PlayerMover: Jump 단계는 Performed입니다.
PlayerMover: Jump 단계는 Canceled입니다.
| 단계 | Button 액션 | Value 액션 |
|---|---|---|
started | 누르기 시작함 | 값이 0에서 벗어남 |
performed | 끝까지 눌림 | 값이 바뀜. 바뀔 때마다 다시 옴 |
canceled | 손을 뗌 | 값이 다시 0이 됨 |
- InputManager의 GetKeyDown > performed, GetKeyUp > canceled과 비슷한 원리입니다.
번외) W를 누르고 있는 동시에 (S or D) 를 같이 눌렀다 떼었을때 어떻게 반응할까?
- D를 눌렀을때

- 왜 Started 한번만 호출되고, Performed는 3번이나 호출된 것일까?
앞서 적어놓은 내용을 보면 알 수 있듯이 InputAction 이 받는 값이 ==Value== 액션이라면
started는 값이 ==0==에서 벗어났을때 호출되고
performed는 값이 바뀔때마다 호출됩니다.
값이 변화하는 흐름을 확인해보면 (0,1) , (1,1) , (0,1) 총 값이 3번 바뀌게 됩니다.
- S를 눌렀을 때

- 왜 D키와 다르게 S키는 Started와 Performed 호출 횟수가 똑같은가?
started는 값이 ==0==에서 벗어났을때 호출된다는 점을 다시 리마인드해보자
W를 누르며 전진하고 있는 상태에서 S를 눌러 후진 입력을 하게 된다면
오브젝트는 전진,후진 둘다 못하는 정지상태가 되게 된다.
그 상태에서 S 입력을 해제하였을때 다시 전진상태로 전환되기 때문에 값이 0에서 벗어나게 된다.



