Sinkronkan Rigidbodies Melalui Jaringan Menggunakan PUN 2

Menyinkronkan Objek di PUN 2 itu sederhana, tetapi bagaimana dengan menyinkronkan Rigidbodies?

Tidak seperti GameObject biasa, Rigidbody juga dipengaruhi oleh Gravitasi (jika bukan Kinematik) dan objek lainnya. Jadi, daripada menyinkronkan Transform objek saja, kita juga perlu menyinkronkan beberapa parameter tambahan, seperti velocity dan angularVelocity.

Dalam postingan kali ini, saya akan menunjukkan cara membuat Rigidbodies interaktif yang dapat dipengaruhi oleh setiap Pemain di Ruangan dan disinkronkan melalui Jaringan.

Unity versi yang digunakan dalam tutorial ini: Unity 2018.3.0f2 (64-bit)

Bagian 1: Menyiapkan PUN 2 dan Contoh Multiplayer

Kami sudah memiliki tutorial cara setting contoh multiplayer menggunakan PUN 2, cek link dibawah ini:

Buat game multipemain di Unity 3D menggunakan PUN 2

Kembalilah setelah Anda selesai menyiapkan proyek multipemain sehingga kami dapat melanjutkan.

Alternatifnya, Anda dapat menghemat waktu dengan mendapatkan proyek sumber dari di sini.

Bagian 2: Menambahkan Benda Kaku Interaktif

Jika Anda mengikuti tutorial di atas, Anda sekarang akan memiliki 2 Adegan "GameLobby" dan "GameLevel"

  • Buka Scene "GameLevel" dan buat beberapa Kubus (GameObject -> 3D Object -> Cube)

  • Tambahkan komponen Rigidbody ke setiap Kubus
  • Tambahkan komponen PhotonView ke setiap Kubus

Sekarang kita perlu membuat Script baru yang akan menyinkronkan Rigidbody melalui jaringan.

  • Buat Script baru dan beri nama PUN2_RigidbodySync

PUN2_RigidbodySync.cs

using UnityEngine;
using Photon.Pun;

public class PUN2_RigidbodySync : MonoBehaviourPun, IPunObservable
{

    Rigidbody r;

    Vector3 latestPos;
    Quaternion latestRot;
    Vector3 velocity;
    Vector3 angularVelocity;

    bool valuesReceived = false;

    // Start is called before the first frame update
    void Start()
    {
        r = GetComponent<Rigidbody>();
    }

    public void OnPhotonSerializeView(PhotonStream stream, PhotonMessageInfo info)
    {
        if (stream.IsWriting)
        {
            //We own this player: send the others our data
            stream.SendNext(transform.position);
            stream.SendNext(transform.rotation);
            stream.SendNext(r.velocity);
            stream.SendNext(r.angularVelocity);
        }
        else
        {
            //Network player, receive data
            latestPos = (Vector3)stream.ReceiveNext();
            latestRot = (Quaternion)stream.ReceiveNext();
            velocity = (Vector3)stream.ReceiveNext();
            angularVelocity = (Vector3)stream.ReceiveNext();

            valuesReceived = true;
        }
    }

    // Update is called once per frame
    void Update()
    {
        if (!photonView.IsMine && valuesReceived)
        {
            //Update Object position and Rigidbody parameters
            transform.position = Vector3.Lerp(transform.position, latestPos, Time.deltaTime * 5);
            transform.rotation = Quaternion.Lerp(transform.rotation, latestRot, Time.deltaTime * 5);
            r.velocity = velocity;
            r.angularVelocity = angularVelocity;
        }
    }

    void OnCollisionEnter(Collision contact)
    {
        if (!photonView.IsMine)
        {
            Transform collisionObjectRoot = contact.transform.root;
            if (collisionObjectRoot.CompareTag("Player"))
            {
                //Transfer PhotonView of Rigidbody to our local player
                photonView.TransferOwnership(PhotonNetwork.LocalPlayer);
            }
        }
    }
}
  • Lampirkan PUN2_RigidbodySync ke kedua Kubus dan tetapkan juga ke Tampilan Foton "Observed Components":

Kita juga perlu melakukan beberapa perubahan pada skrip PUN2_PlayerSync dari tutorial Multiplayer:

  • Buka PUN2_PlayerSync.cs
  • Di void Start(), di dalam if(photonView.IsMine) tambahkan kode ini:
            //Player is local
            gameObject.tag = "Player";
            //Add Rigidbody to make the player interact with rigidbody
            Rigidbody r = gameObject.AddComponent<Rigidbody>();
            r.isKinematic = true;

Jadi sekarang void Start() akan terlihat seperti ini:

    // Use this for initialization
    void Start()
    {
        if (photonView.IsMine)
        {
            //Player is local
            gameObject.tag = "Player";
            //Add Rigidbody to make the player interact with rigidbody
            Rigidbody r = gameObject.AddComponent<Rigidbody>();
            r.isKinematic = true;
        }
        else
        {
            //Player is Remote, deactivate the scripts and object that should only be enabled for the local player
            for (int i = 0; i < localScripts.Length; i++)
            {
                localScripts[i].enabled = false;
            }
            for (int i = 0; i < localObjects.Length; i++)
            {
                localObjects[i].SetActive(false);
            }
        }
    }

Dengan menambahkan komponen Rigidbody kami memastikan bahwa instance pemain dapat berinteraksi dengan Rigidbodies lain dan dengan mengubah tag menjadi "Player" kami dapat mendeteksi apakah instance lokal yang bertabrakan dengan Rigidbody.

  • Simpan Scene GameLevel setelah semuanya selesai.

Sekarang mari kita buat dan ujilah!

Sharp Coder Pemutar video

Semuanya berfungsi seperti yang diharapkan, sekarang Rigidbodies dapat disinkronkan melalui Jaringan sambil tetap dapat berinteraksi.

Artikel yang Disarankan
Buat Game Multiplayer di Unity menggunakan PUN 2
Buat Game Mobil Multi Pemain dengan PUN 2
Kompensasi Lag PUN 2
Unity Menambahkan Obrolan Multipemain ke Ruang PUN 2
Panduan Pemula Jaringan Foton (Klasik).
Membangun Game Jaringan Multipemain dalam Unity
Kompresi Data Multi Pemain dan Manipulasi Bit