Tanks, Multiplayer with PUN! (Part 5)
Tank의 포탄사격 방식의 경우, 어떻게 하면 멀티플레이어 접속 시 동기화해서 표시 또는 동기화 요소의 효과를 낼 수 있을까요? 이번 편에서는 2가지 방식으로 만들어보겠습니다. 하나는 전 편에서 소개한 PhotonNetwork.Instantiate이고, 다른 하나는 Photon 내의 PunRPC(Remote Procedure Call)“원격 절차 호출”을 사용하는 것입니다. 🤖
포탄 사격 실제상황!
상기 GIF 애니메이션은 바로 우리 프로젝트 실행 시의 포탄사격 실제 상황입니다!
그렇다면 먼저 첫 번째 방법을 사용해 보겠습니다~
Method A : PhotonNetowrk.Instantiate
앞서 2편에서 만약 오브젝트가 다른 Client에서 동일한 위치/회전/크기 등의 정보를 표시해야 한다면, PhotonView & PhotonTransformView를 반드시 사용해야 한다고 했습니다. 따라서 우리는 먼저 기존 범례의 포탄 설정을 보겠습니다. Assets → Complete → Prefabs → CompleteShell의 경로에서 다음의 화면을 볼 수 있습니다.
기존 범례의 포탄 Complete → Prefabs → CompleteShell
기존 범례의 CompleteShell을 1부 복사하고 Photon View와 Photon Transformer View를 추가한 후 우리의 프로젝트 TanksPUN → Resources 아래 넣습니다. 새로운 포탄 Prefab의 설정 화면은 다음과 같습니다.
PhotonView & PhotonTransformView의 포탄을 추가
이렇게 우리는 TankShooting.cs 중의 Fire()에서 Instantiate를 PhotonNetwork로 변경하는 방식으로 새로운 GameObject 네트워크 동기화를 구현할 수 있습니다~
private void Fire()
{
m_Fired = true;
GameObject shellInstance = PhotonNetwork.Instantiate(
"CompleteShell",
m_FireTransform.position,
m_FireTransform.rotation,
0);
Rigidbody body = shellInstance.GetComponent<Rigidbody>();
body.velocity = m_CurrentLaunchForce * m_FireTransform.forward;
m_ShootingAudio.clip = m_FireClip;
m_ShootingAudio.Play ();
m_CurrentLaunchForce = m_MinLaunchForce;
}
이처럼 게임에서 우리가 포탄 발사키(Enter or Spacebar)를 누르기만 하면, 다른 동일한 게임 룸 내의 플레이어는 모두 화면 상에서 포탄이 발사되는 것(동시표시)을 볼 수 있습니다~👾
주의: 좌측 화면에서 둥근 원 안의 오브젝트, 이것은 네트워크 동기화 표시 Pos/Rot/Scale !
네트워크 동기화 표시 포탄에 어떤 차이가 있을까요? 아~ 우리는 Photon Transform View의 Position+Rotation만을 이용하기 때문에 변동이 있는 위치 정보만을 동기화합니다. 🐶
이어서 다른 방식을 살펴보겠습니다~
Method B: [PunRPC]
원격 절차 호출 방식은 프로그램에서 [PunRPC]가 tag를 사용하며, PUN에 어느 절차가 원격단(Remote Client)에 의해 호출될 수 있는지를 알려줍니다. 동시에 [PunRPC]에 의해 표기된 절차를 사용하여 photonView.RPC로 호출합니다. 따라서 다음 TankShooting의 Bass Class를 Photon.MonoBehaviour로 정정해야 하며, 이 Photon에서 제공하는 MonoBehaviour를 사용하면 그 내부에 다른 어떤 일이 있는지 걱정할 필요가 없습니다. 가장 중요한 것 역시 기존의 class를 photonView에서 제공하는 추가 기능에 사용할 수 있도록 만드는 것입니다.
현재 우리가 이 방식을 사용할 때 주의해야 할 부분을 정리해 보겠습니다.
- 유형은 MonoBehaviour를 승계해야 합니다.
- Using [PunRPC] tag, 의미는 PUN Remote Procedure Call입니다.
- RPC를 사용해 [PunRPC] tag의 절차를 호출합니다.
public class TankShooting : Photon.MonoBehaviour
{
...
private void Fire()
{
m_Fired = true;
Rigidbody shellInstance = Instantiate (m_Shell, m_FireTransform.position, m_FireTransform.rotation) as Rigidbody;
photonView.RPC("FireOther", PhotonTargets.Others, m_FireTransform.position);
shellInstance.velocity = m_CurrentLaunchForce * m_FireTransform.forward;
m_ShootingAudio.clip = m_FireClip;
m_ShootingAudio.Play ();
m_CurrentLaunchForce = m_MinLaunchForce;
}
[PunRPC]
void FireOther(Vector3 pos)
{
m_Fired = true;
Rigidbody shellInstance =
Instantiate (m_Shell, pos, m_FireTransform.rotation) as Rigidbody;
shellInstance.velocity = m_CurrentLaunchForce * m_FireTransform.forward;
m_CurrentLaunchForce = m_MinLaunchForce;
}
...
}
이처럼 게임에서 우리가 포탄 발사키(Enter or Spacebar)를 누르기만 하면, 다른 동일한 게임 룸 내의 플레이어는 모두 화면 상에서 포탄이 발사되는 것을 볼 수 있습니다. 중요한 것은 생성된 포탄은 각 플레이어 게임 공간에서의 실체로서, 네트워크 동기화 표시된 것이 아니라는 것입니다~😬👻👏🏻
[PunRPC]의 방식으로 각 플레이어에게 생성된 포탄 실체
Method A and B의 차이점과 같은점 및 사용시기
여러분, 위의 2가지 방법으로 생성한 포탄에 어떤 차이점이 있는지 발견하셨나요? 게임에는 어떠한 영향을 미칠까요?
Method A에서 사용한 것은 동기화 위치 정보입니다. 그 네트워크 상의 오브젝트는 Clone에서 나온 것으로서 위치가 지속될 경우에만 PUN에 의해 동기화됩니다. 기존 버전의 서브젝트가 어느 Client에서 생성된 것을 보면 바로 그것이 주요한 변동권을 가진다는 것을 알 수 있습니다. 다른 정보는 자체적으로 다시 대응하는 이벤트를 프로그래밍해야 하는데, 예를 들어 표시 여부, 이미 폭발했는지의 여부, 점수계산 여부 등이 있습니다.
Method B에서 사용한 것은 “원격 절차 호출”입니다. 따라서 자신의 Client에 하나의 진짜 포탄을 생성하는 것 외에도, 다른 Client도 동일한 위치에 호출해 동일한 속도와 방향의 포탄을 생성하도록 합니다. 따라서 생성된 것이 바로 실체이고, 다른 네트워크 상의 Client의 포탄을 따라 동기화되지 않습니다. 네트워크의 지속적인 동기화 정보 전송이 줄어들기 때문에 그 실행효과가 아주 빠릅니다.
[PunRPC]의 방법은 여기에서 단지 간단한 포탄 생성용으로 사용됐으나 많은 부분에서 응용할 수 있습니다. 예를 들어 메시지 전송, 특정 Client의 오브젝트 취득, 정보 교환, 모든 Client에 대해 특정 이벤트 진행 등이 있는데, 그 용도는 아주 다양합니다!
이어서, 아직 더 많은 문제를 상상해볼 수 있습니다. Tank의 생명치/상해/사망/부활과 같이 실제 게임에서 우리는 어떻게 네트워크 동기화를 구현할 수 있을까요? 그건~ 게임 설계 방식은 수백 가지가 있기 때문에, 우리가 어떻게 이러한 편리한 Photon Cloud/Server를 운용하는가에 달려 있습니다~ 또한 이 2가지 방식은 실제 게임 설계 상에서 모두 강점을 가지고 있습니다. 여기에서는 공간적인 제약상 간단한 입문 응용만 소개했는데, 좀더 단계가 높은 부분은 나중에 또 말씀드리도록 하겠습니다~ 🤖👻💕👾🎮
게임 설계의 길은 많고 많으니 서로 정보를 교환해 가도록 해요~
댓글
댓글 0개
댓글을 남기려면 로그인하세요.