UNET連線遊戲(三){廝殺吧!!吃下我的子彈}

本篇使用的是5.3版後有UNET的UNITY
目標:基本連線遊戲機制+發射物體和其他玩家互動(攻擊)
1.延續前篇(UNET連線遊戲(二){讓子彈飛一毀})

  • 邏輯概念:人物被子彈擊中要產生相應的處理,因此需要掛載一個程式在人物身上,來判斷是否被擊中。
    透過此程式呼叫SERVER讓SERVER回覆PLAYER發生了什麼事情。
  • 首先簡單改寫一下原來子彈的內容
    希望子彈在擊中目標後也會消失

    using UnityEngine;
    using System.Collections;
    using UnityEngine.Networking;
    public class AmmoController : NetworkBehaviour
    {
    	private float lifeTime;
    	public float maxTime = 3.0f;
    	void Start ()
    	{
    		lifeTime = 0.0f;
    	}
    	[ServerCallback]
    	void Update ()
    	{
    		lifeTime += Time.deltaTime;
    		if( lifeTime > maxTime )
    		{
    			NetworkServer.Destroy(gameObject);
    		}
    	}
    }

     

  • 在原來的AmmoController.cs裡面(如上)改為下方的內容
    using UnityEngine;
    using System.Collections;
    using UnityEngine.Networking;
    public class AmmoController : NetworkBehaviour
    {
    	private float lifeTime;
    	public float maxTime = 3.0f;
    	void Start ()
    	{
    		lifeTime = 0.0f;
    	}
    	[ServerCallback]
    	void Update ()
    	{
    		lifeTime += Time.deltaTime;
    		if( lifeTime > maxTime )
    		{
    			DestroyAmmo();//改由方法銷毀
    		}
    	}
    	public void DestroyAmmo(){
    		NetworkServer.Destroy(gameObject);
    	}
    }

    新增一個public的子彈銷毀程式DestroyAmmo()來執行銷毀

  • 順手加些特效到子彈中
    到Resources下找的我們的子彈,並且拉到Hierarchy中準備編輯一下
    unet-hit-004
  • 匯入官方提供的粒子素材
    unet-hit-002
    找到適合的素材(這裡使用FireComplex)拖曳到Ammo上當成子物件
    unet-hit-005
    並且歸零FireComplex在Ammo內的座標位置(重合座標位置)
    *這裡可以選擇關閉或刪除Ammo原來的MeshRenderer
    (隱藏原來的球體模型,只保留碰撞器)
  • 設置完畢按下Apply更新Prefab,刪除場景上的Ammo
    unet-hit-006
  • 到此步因該可以完成:
    子彈的特效、撞擊人物消失

2.與人物互動

  • 接著撰寫DamageScript.cs並添加至人物
    using UnityEngine;
    using System.Collections;
    using UnityEngine.Networking;
    public class DamageScript : NetworkBehaviour {
    	AudioSource damageAudio;
    	void Awake()
    	{
    		damageAudio = GetComponent<AudioSource>();
    	}
    	void OnCollisionEnter(Collision other)
    	{
    		if (other.gameObject.name == "Ammo") {
                            other.gameObject.GetComponent<AmmoController> ().DestroyAmmo ();
    			CmdHitPlayer(this.transform.gameObject);
    		}
    	}
    	[Command]
    	void CmdHitPlayer(GameObject g)
    	{
    		g.GetComponent<DamageScript>().RpcResolveHit();
    	}
    	[ClientRpc]
    	public void RpcResolveHit()
    	{
    		if (isLocalPlayer)
    		{
    			damageAudio.Play ();
    			Transform spawn = NetworkManager.singleton.GetStartPosition();
    			transform.position = spawn.position;
    			transform.rotation = spawn.rotation;
    		}
    	}
    }

    AudioSource damageAudio; 可以用來播放打擊音效
    OnCollisionEnter偵測撞擊物是否名稱為Ammo
    取得Ammo上的控制程式並通知SERVER銷毀
    以及回報玩家狀態
    [Command]的下方CmdHitPlayer方法用來跟SERVER提示使用RpcResolveHit方法回覆玩者
    [ClientRpc]下的方法同樣必須宣告為public便於呼叫
    若玩家被擊中將其打回重生點

  • 若不想一擊斃命也可以改寫RpcResolveHit()裡的功能
    且在上方多宣告一個int HP = 3; (3滴血可自行設定)

    [ClientRpc]
    	public void RpcResolveHit()
    	{
    		if (isLocalPlayer)
    		{
    			if (HP > 1) {
    				HP--;
    				damageAudio.Play ();
    			} else {
    				Transform spawn = NetworkManager.singleton.GetStartPosition();
    				transform.position = spawn.position;
    				transform.rotation = spawn.rotation;
    				HP = 3;
    			}
    		}
    	}

     

下期預告:UNET連線遊戲(四){我快死了,HP_UI}

在〈UNET連線遊戲(三){廝殺吧!!吃下我的子彈}〉中有 1 則留言

發佈留言

發佈留言必須填寫的電子郵件地址不會公開。 必填欄位標示為 *