Home > Unity > Netcode > Unity Netcode 따라하기 Hello World

Unity Netcode 따라하기 Hello World
Unity Netcode Unet Network

Hello World

Hello World 학습 문서
본 게시글은 해당 문서를 학습하며 정리한 게시글 입니다.

Netcode 설치하기
해당 게시글에 Netcode 설치 및 프로젝트 생성까지 소개 한다.

Network Manager 설정 하기

프로젝트를 생성하고 Netcode Package를 설치까지 했다면, Hierarchy View빈 오브젝트를 생성해준다.
오브젝트의 이름은 NetworkManager로 설정한다.
이 때 해당 이름과 동일한 오브젝트를 여러개 만들면 안된다. 단 하나만 존재해야 한다.

오브젝트 생성후 해당 오브젝트를 클릭 하여 Inspector View에서 하단에 있는 Add Component 버튼을 클릭한다.
여러 카테고리가 나오는데 [Netcode] - [Network Manager]를 클릭해 컴포넌트를 추가해준다.

Netcode_Add_NetworkManager_Object Netcode_Add_NetworkManager_01 Netcode_Add_NetworkManager_02

추가 후 Inspector View에 표기되는 NetworkManager.csfield
Network Transport 하단에 select transport를 클릭해 Unity transport를 선택해준다.
*(Unet Transport도 있지만 Unity 2022.2 버전 이후 부터는 지원하지 않는다고 한다.)

Netcode_Select_Transport
**각각의 작업이 끝나면 Scene을 저장해 안전하게 작업하자! **

Network Manager Player Prefab 설정 하기

Hierarchy View에 원하는 3D 오브젝트를 생성한다. (Plan 오브젝트는 추후 Ground로 사용할 예정이니 제외하면 좋을 것 같다.)
생성후 이름을 Player 혹은 자신이 원하는 이름으로 설정해 준다.

Inspector View에서 Add Component 버튼을 클릭하여 [Netcode] - [Network Object]를 클릭해 컴포넌트를 추가해준다.

Netcode_Add_NetworkObject_01 Netcode_Add_NetworkObject_02

Project View에서 Assets 폴더로 이동해준다.(건드리지 않았다면 기본 Assets 폴더일 것이다.)
우클릭하여 Prefabs 이름의 폴더를 추가 해준다.

Hierarchy View에서 Player(NetworkObject 컴포넌트를 추가한 오브젝트)를 좌클릭으로 드래그해서 Prefabs 폴더에 넣어준다.
해당 오브젝트의 Prefab이 생성 되었다.
Hierarchy View에 드래그 했던 오브젝트를 삭제 해준다.(NetworkObject를 포함한 오브젝트는 미리 배치하면 안된다.)
Netcode_Create_Prefab

NetworkManager 오브젝트를 클릭해 Inspector View에서 NetworkManager 컴포넌트의 FieldPlayer PrefabNetworkPrefabs에 생성한 Prefab을 추가 해준다.

Netcode_Add_Player_Prefab_01 Netcode_Add_Player_Prefab_02

테스트 하기 위해 굳이 필요한 사항은 아니지만 Hierarchy View에 3D Object 중 Plan을 추가해 (0, 0, 0)에 위치시켜준다.
Player와 구분 하기 편하게 나는 색상을 추가 해줬다. 색상 변경은 Project View에서 [우클릭] - [Create] - [Material]을 추가해 원하는 색상을 고르고 원하는 오브젝트에 드래그 하여 넣어주면 된다.

Project Build

여기 까지 만들었다면 Editor에서 플레이를 해도 실행 되는 것을 볼 수 있다. 그럼 플레이 버튼을 눌러 보면…..
해당 화면만 나오게 된다. 버튼도, 안내 문구도 없어서 당황 할 수 있다.
Netcode_Play_Screen

Hierarchy View에서 NetworkManager를 클릭하고 Inspector View에서 해당 버튼을 클릭하면 아까 만들었던 Player Prefab이 생성 된다.
(Server와 Client는 각각 Client와 Server가 있어야 상호작용이 된다. Editor만 실행해서는 아무 일도 안일어난다.)
Netcode_Play

Build Setting

Server와 여러 Client를 만들기 위해 해당 ProjectBuild해보자.
상단 도구 Tool에서 [File] - [Build Settings…]을 클릭하면 해당 팝업창이 뜬다.
Netcode_Build_Setting

여기서 [Add Open Scenes]을 누르면 현재 오픈된 SceneBuild에 추가된다.
(현재 오픈된 Scene은 Hierarchy View 상단에서 볼 수 있다.)
현재 선택된 Platform이 원하는 Platform인지 확인 후 Build 버튼을 누르면 끝 이다.
그 전에 아래 글을 읽고 필요하다면 아래 먼저 진행 하면 된다.

Player Setting

현재는 필요 없지만 Build Settings 팝업창에서 [Player Settings..]를 누르면 Player Setting 팝업창이 뜬다.
Netcode_Build_Player_Setting

해당 팝업창에서는 곧바로 Player에 관한 설정을 하는 창이 나오는데 Build된 프로젝트의 아이콘, 버전, 이름, 만든 회사 이름 실행시 창 크기(Windows, Mac, Linux) 등등 Build 되었을 때 표시할 것들에 대해 설정하는 창이다. 해당 창에서 Company NameScreen 크기를 수정하려 한다.
Company Name은 추후 Debug 관련 로그를 볼 수 있는 폴더가 생성될 때 해당 이름으로 생성되기 떄문에 찾기 편하려고 변경하는 것이고 Screen 크기는 defaultFull Screen으로 되어있어 불편해서 변경한다.
표시된 곳을 수정하고 다시 Build Settings 팝업창으로 돌아와 Build 해주면 된다.
(Project Settings 팝업창은 수정 후 닫으면 Build시 자동 적용된다. 단, 몇몇 Apply 버튼이 존재하는 것은 해당 버튼을 눌러줘야 적용된다.)

Build가 끝나면 자동으로 Build시 설정한 폴더가 열린다.(나는 프로젝트 폴더에 만들었다.)
하지만 아직 Server 또는 Client를 구분지어 주는 기능이 없기 때문에 Command line(cmd)으로 설정해주어야 한다.
(아무리 .exe 실행파일을 여러개 띄어도 Player Prefab은 생성되지 않는다.)

Command Line(Cmd 설정)

cmd창 익숙한 사람도 있을테고, 복잡해보여서 싫어하는 사람도 있을 것 같다. cmd창에서 여러 명령어를 다루는 것이 아니니 너무 걱정 말고 진행해도 된다.
(이후에 Server, Client, Host를 구분짓는 기능이 프로그램에 추가되니 cmd로 미리 경혐해보고 싶은 사람만 해도 될 것 같다.)

드디어 직접 코드를 타이핑 할 수 있는 부분이 왔다. (물론 복사 붙여넣기를 해도 된다.)
Project View에서 [Aseets] 폴더에 [Scripts] 폴더를 생성하여 그안에 C# 파일을 만든다.
이름은 원하는 이름을 사용해도 된다. 나는 NetworkCommandLine으로 만들었다.

사용할 코드는 아래와 같다.

해당 코드는 cmd창에서 명령어를 적었을 때 명령어에 따라 기능을 실행 해주는 코드다.
|NetworkCommandLine.cs|

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using Unity.Netcode;
public class NetworkCommandLine : MonoBehaviour
{
    private NetworkManager netManager;

    void Start()
    {
        // 부모 오브젝트의 NetworkManager Component를 읽어온다. 
        // 즉, 해당 오브젝트는 NetworkManager Component를 가진 오브젝트의 하위 오브젝트로 만들어야 한다.
        netManager = GetComponentInParent<NetworkManager>();

        if (Application.isEditor) return; // Editor에서는 실행 되지 않게 한다.

        var args = GetCommandlineArgs(); // 명령어를 읽어 온다.

        if(args.TryGetValue("-mlapi", out string mlapiValue))
        {
            switch(mlapiValue)
            {
                case "server":
                    netManager.StartServer();
                    break;
                case "host":
                    netManager.StartHost();
                    break;
                case "client":
                    netManager.StartClient();
                    break;
            }
        }
    }

    private Dictionary<string, string> GetCommandlineArgs()
    {
        Dictionary<string, string> argDictionary = new Dictionary<string, string>();

        // cmd창에서 입력한 명령어를 공백을 기준으로 배열로 반환해 읽어온다.
        var args = System.Environment.GetCommandLineArgs();

        for(int i = 0; i < args.Length; i++)
        {
            var arg = args[i].ToLower();

            // '-'문자로 시작하는지 확인한다.
            if(arg.StartsWith("-"))
            {
                // 해당 문자열이 배열의 마지막인지 확인 후 아니라면 다음 인덱스의 문자열을 저장한다.
                var value = i < args.Length - 1 ? args[i + 1].ToLower() : null;

                // 저장한 문자열이 '-'문자로 시작한다면 다시 null로 초기화 한다.
                value = (value?.StartsWith("-") ?? false) ? null : value;

                argDictionary.Add(arg, value);
            }
        }
        return argDictionary;
    }
}

코드 주석에 적은 그대로이다. 해당 코드는 cmd창에서 입력한 토큰을 읽어와 공백을 기준으로 배열로 만든 값을
조건에 맞는 값인지 확인한 후 해당 값을 내보낸다.
호환하는 명령어는 -mlapi [원하는 값] 이며 값은 Server, Client, Host 세개의 값을 처리해준다.

주석에 적혀있듯이 해당 코드는 NetworkManager.cs컴포넌트로 가지는 오브젝트의
하위 오브젝트컴포넌트로 넣어줘야 한다.

Hierarchy View에서 NetworkManager를 찾아 선택한 후 [우클릭] - [Create Empty]를 눌러 빈 오브젝트를 만들어 준다.
생성한 오브젝트를 클릭해 Inspector View에서 [Add Component] - NetworkCommandLine을 검색해 추가해 준다.
(Project View에서 해당 .cs파일을 드래그해 오브젝트에 넣어도 된다.)
이제 다시 한번 Build해준다.

cmd 실행

Build가 완료 되었다면 cmd를 실행 시킨다.
Build가 된 파일들이 있는 폴더를 알아야 한다.
나같은 경우 [C드라이브] - [Users] - [설정한 이름] - [Unity_Netcode] - [Build] - .exe 파일
이렇게 저장되어있다.
cmd를 따로 설정하지 않았다면 [설정한 이름] 위치에서 시작할 것이다.
C:Users\설정한이름> 일텐데, 다른 폴더라면
C:Users\설정한이름>cd \ 를 사용해 최상위 폴더(해당 드라이브)로 이동할 것이다.
그 뒤 cd 명령어를 사용해서 편안한 위치로 옮기던가 최상위 폴더부터 시작해도 된다.

나의 경우
C:Users\설정한이름>Unity_Netcode\Build\Unity_Netcode.exe -mlapi server
해당 명령어를 사용해 실행 시켰다. 이렇게 명령어를 사용하면 .exe파일 즉, 실행파일 까지의 문구는 제외하고
다음 문구부터 전달 된다. 코드에서 보았듯이 -(하이픈)이 붙은 문자열 다음 문자열을 읽어 사용하는 방식이므로
해당 명령어는 server의 기능을 하는 프로젝트를 실행시킨다.

Netcode_Build_Play_Server

하지만 server만 실행 시켜서는 아무것도 나오지 않는다. client도 같이 실행 시켜주자.
C:Users\설정한이름>Unity_Netcode\Build\Unity_Netcode.exe -mlapi client
클라이언트를 실행 하니 서버와 해당 클라이언트에 같은 Player가 생성 되었다.
이외에도 EditorBuild실행파일은 서로 호환가능하니 여러 가지를 확인 할 수 있다.
다만, 현재는 Player가 한자리에서만 생성되어 실행파일에서는 확인이 어렵고 Editor에서는 추가되는 Player Object를 확인 할 수 있다.
Netcode_Build_Play_Server_Client