Skip to content

Unity New Input System

Unity의 New Input System(com.unity.inputsystem)은 기존 Input.GetKeyDown 방식을 대체하는 이벤트 기반 입력 처리 시스템입니다. 플랫폼 독립적인 바인딩, 런타임 리매핑, 로컬 멀티플레이어 지원이 핵심 특징입니다.


항목구 Input ManagerNew Input System
폴링 방식Update마다 직접 폴링이벤트 기반 콜백
바인딩에디터 고정에셋 파일로 관리, 런타임 리매핑
멀티 디바이스미지원기기별 독립 처리
로컬 멀티플레이어수동 구현PlayerInputManager 내장
테스트어려움InputTestFixture 제공

타입역할
InputAction단일 입력 동작 (Jump, Fire 등)
InputActionMap연관 Action 묶음 (Gameplay, UI 등)
InputActionAsset전체 입력 설정을 담는 에셋 파일 (.inputactions)
PlayerInput컴포넌트 기반 입력 연결
PlayerInputManager로컬 멀티플레이어 관리
타입특징사용 예
Button눌림/뗌 이벤트Jump, Fire
Value연속 값 변화Move (Vector2), Look
PassThroughValue와 동일하나 인터랙션 없음마우스 포지션

using UnityEngine;
using UnityEngine.InputSystem;
public class PlayerController : MonoBehaviour
{
InputAction _moveAction;
InputAction _jumpAction;
void Awake()
{
// 코드로 직접 바인딩 정의
_moveAction = new InputAction("Move", InputActionType.Value);
_moveAction.AddCompositeBinding("2DVector")
.With("Up", "<Keyboard>/w")
.With("Down", "<Keyboard>/s")
.With("Left", "<Keyboard>/a")
.With("Right", "<Keyboard>/d");
_jumpAction = new InputAction("Jump", InputActionType.Button);
_jumpAction.AddBinding("<Keyboard>/space");
_jumpAction.AddBinding("<Gamepad>/buttonSouth");
_jumpAction.performed += OnJump;
}
void OnEnable()
{
_moveAction.Enable();
_jumpAction.Enable();
}
void OnDisable()
{
_moveAction.Disable();
_jumpAction.Disable();
}
void Update()
{
Vector2 move = _moveAction.ReadValue<Vector2>();
transform.Translate(new Vector3(move.x, 0, move.y) * Time.deltaTime * 5f);
}
void OnJump(InputAction.CallbackContext ctx)
{
Debug.Log("점프!");
}
void OnDestroy()
{
_jumpAction.performed -= OnJump;
_moveAction.Dispose();
_jumpAction.Dispose();
}
}

.inputactions 에셋 파일을 생성하면 에디터 GUI로 바인딩을 관리하고 C# 래퍼 클래스를 자동 생성할 수 있습니다.

Project → Create → Input Actions → PlayerInputActions.inputactions
Inspector → Generate C# Class 체크 → Apply
public class PlayerController : MonoBehaviour
{
PlayerInputActions _actions; // 자동 생성 클래스
void Awake()
{
_actions = new PlayerInputActions();
_actions.Gameplay.Jump.performed += OnJump;
}
void OnEnable() => _actions.Gameplay.Enable();
void OnDisable() => _actions.Gameplay.Disable();
void Update()
{
Vector2 move = _actions.Gameplay.Move.ReadValue<Vector2>();
transform.Translate(new Vector3(move.x, 0, move.y) * Time.deltaTime * 5f);
}
void OnJump(InputAction.CallbackContext ctx) => Debug.Log("점프!");
void OnDestroy()
{
_actions.Gameplay.Jump.performed -= OnJump;
_actions.Dispose();
}
}

Player Input 컴포넌트 vs 코드 바인딩

Section titled “Player Input 컴포넌트 vs 코드 바인딩”
항목PlayerInput 컴포넌트코드 바인딩
설정 방법Inspector GUIC# 코드
이벤트 전달SendMessage / UnityEvent / C# Event직접 콜백 등록
로컬 멀티플레이어PlayerInputManager 연동 용이수동 관리
권장 용도프로토타입·단일 플레이어프로덕션·성능 중시

로컬 멀티플레이어 (PlayerInputManager)

Section titled “로컬 멀티플레이어 (PlayerInputManager)”
// PlayerInputManager 컴포넌트를 씬에 배치
// Joining Behavior: Join Players When Join Action Is Triggered
public class MultiplayerSetup : MonoBehaviour
{
void OnEnable()
{
PlayerInputManager.instance.onPlayerJoined += OnPlayerJoined;
PlayerInputManager.instance.onPlayerLeft += OnPlayerLeft;
}
void OnDisable()
{
PlayerInputManager.instance.onPlayerJoined -= OnPlayerJoined;
PlayerInputManager.instance.onPlayerLeft -= OnPlayerLeft;
}
void OnPlayerJoined(PlayerInput player)
{
Debug.Log($"플레이어 {player.playerIndex} 참가 — 기기: {player.devices[0].displayName}");
// 각 PlayerInput 인스턴스는 서로 다른 기기에 자동 바인딩
}
void OnPlayerLeft(PlayerInput player)
{
Debug.Log($"플레이어 {player.playerIndex} 퇴장");
}
}

구 Input Manager 마이그레이션 전략

Section titled “구 Input Manager 마이그레이션 전략”
  1. 패키지 설치: Package Manager → Input System → Install
  2. 백엔드 전환: Project Settings → Player → Active Input Handling → Both (전환 기간 동안 양쪽 허용)
  3. 점진적 교체: 모듈별로 Input.GetKeyInputAction으로 교체
  4. 테스트: InputTestFixture로 입력 이벤트를 시뮬레이션하여 자동화 테스트 작성
  5. 최종 전환: Active Input Handling → Input System Package (New) 로 변경
// InputTestFixture 예시
using NUnit.Framework;
using UnityEngine.InputSystem;
using UnityEngine.InputSystem.Utilities;
public class PlayerTests : InputTestFixture
{
[Test]
public void PressSpaceTriggersJump()
{
var keyboard = InputSystem.AddDevice<Keyboard>();
var controller = new PlayerController();
Press(keyboard.spaceKey);
// Jump 이벤트 발생 검증
}
}