這兩天研究了一下unity的尋路系統跟攝像機的一些東西
在遊戲中,我們經常會用到尋路這個功能,以前的做法多數是使用A*算法
而unity中自己帶有了一套尋路系統供我們使用,關於這個這個用法,我們可以從《unity 4.x從入門到精通》的第九章瞭解到如何生成一個尋路網格
本文重點是展示這個尋路系統的使用效果,結合《unity 4.x從入門到精通》上攝像機相關的知識(185-189頁),來做一個人物尋路,然後小地圖顯示場景效果
本文unity版本爲4.6版本,用到的技術要點如下:
1.unity自帶的尋路系統
2.理解鼠標點擊2D屏幕,用射線方式映射到世界3D座標,確定移動的目標點
3.攝像機畫中畫技術
4.攝像機跟隨物體技術
5.UGUI的使用
好,現在我來一步步講解我的製作過程
首先我們創建一個空的GameObject,用於裝載地面,阻礙物,模擬人物等物體,
接着我們創建一個plane作爲我們的地面,修改他的scale爲10,1,10
然後我們創建一個sphere做作爲我們的模擬人物,創建後,添加Nav Mesh Agent控件
創建三個cube作爲我們的阻礙物,這三個cube需要設置爲static,不然生成尋路網格的時候會無效
加一個平行光照到我們的plane上
創建一個點燈源,稍後作爲我們鼠標點擊位置的示意用
場景效果如下圖所示
生成尋路網格點擊Window->Navigation,在Object那裏選擇All後,直接點擊Bake按鈕生成就可以
生成後,會在你存放場景的目錄下有一個跟場景名一樣的文件夾,裏面放着網格信息的
接着,我們用UGUI來建一個UI,它的右上角顯示小地圖的
直接點擊GameObject->UI->RawImage來建立一個UGUI的UI系統,然後調整RawImage的大小爲128X128
然後我們新建一個攝像機,命名爲textureCamera
新建UGUI的Canvas下的Render Mode選Screen space overlay就可以了,意思就是覆蓋在屏幕之上
爲何我們要用RawImage,因爲我們注意到,攝像機有一個叫做targetImage的成員參數,這個參數是用於存儲攝像機映射場景畫面到這個targetImage上去的
這個參數初始值爲空,需要我們自己建立一個RenderTexture對象去傳給它,設置了這個參數之後,這個攝像機的畫面就不會自動合併到我們的屏幕上去了
需要我們用腳本控制顯示這個targetImage才能看到這個攝像機原本看見的畫面
我們就用此原理來達到製作小地圖的效果
整個場景對象結構圖如下
下面貼一下用到的腳本
1.角色控制腳本,主要接受鼠標點擊,然後轉換到世界座標上去,然後通知人物走到那個位置
using UnityEngine;
using System.Collections;
public class PlayerController : MonoBehaviour {
private NavMeshAgent man;
public Transform pointLightPos;
// Use this for initialization
void Start () {
man = GetComponent<NavMeshAgent>();
if (null == pointLightPos)
{
pointLightPos = GameObject.Find("Point light").transform;
}
}
// Update is called once per frame
void Update () {
//man.SetDestination(targetPos.position);
//按下了鼠標左鍵,就發出射線
if (Input.GetMouseButtonDown(0))
{
//調用射線函數檢測
Ray ray = Camera.main.ScreenPointToRay(Input.mousePosition);
RaycastHit hit;
if (Physics.Raycast(ray, out hit))
{
//檢測到碰撞就設置點光燈的位置
pointLightPos.position = new Vector3(hit.point.x,transform.position.y,hit.point.z);
man.SetDestination(hit.point);
}
}
}
}
把上面的playercontroller.cs綁定到player的物體對象上去,並拉點燈源到那個pointLisht去
另外這裏說一下,我發現這個鼠標點擊映射到世界座標中主要是按Main Camera的座標去映射的,其他的Camera要通過寫特殊腳本的方式去映射
大家可以試試,這裏mark一下
2.地圖攝像機中的targertTexture替換腳本
using UnityEngine;
using System.Collections;
public class CameraController : MonoBehaviour {
private RenderTexture renderTexture;
Camera textureCamera;
// Use this for initialization
void Start () {
//創建一個臨時的RenderTexture,給攝像機的targetTexture存儲攝像機畫面用
renderTexture = RenderTexture.GetTemporary(128, 128, 24, RenderTextureFormat.ARGB32);
renderTexture.isPowerOfTwo = false;
renderTexture.useMipMap = false;
//獲取攝像機組件,然後設置targertTexture
textureCamera = GetComponent<Camera>();
textureCamera.targetTexture = renderTexture;
}
// Update is called once per frame
void Update () {
}
}
把這個腳本綁定到textureCamera上去
3.UGUI上顯示小地圖的控制腳本
using UnityEngine;
using UnityEngine.UI;
using System.Collections;
public class ShowImage : MonoBehaviour {
private RawImage rawImage;
public Camera textureCamera = null;
// Use this for initialization
void Start () {
rawImage = GetComponent<RawImage>();
if (null == textureCamera)
{
textureCamera = GameObject.FindGameObjectWithTag("texturecamera").GetComponent<Camera>();
}
}
// Update is called once per frame
void Update () {
//直接使用攝像機的targetTexture替換
rawImage.texture = textureCamera.targetTexture;
}
}
把這個腳本綁定在UGUI中的RawImage中區4.主攝像機設置跟隨在人物後面,動態跟隨
using UnityEngine;
using System.Collections;
public class CameraFollow : MonoBehaviour {
public GameObject player;
private Camera camera;
// Use this for initialization
void Start () {
camera = GetComponent<Camera>();
}
// Update is called once per frame
void Update () {
//計算攝像機位置
Vector3 newPos = player.transform.position + (-20.0f * player.transform.forward) + new Vector3(0.0f,20.0f,0.0f);
transform.position = newPos;
//設置攝像機的攝像方向爲對着物品方向
transform.rotation = Quaternion.LookRotation(player.transform.position - transform.position);
}
}
把這個腳本綁定到Main Camera中區
好了最後看看我做的東西最後做到的效果
最後我上傳一下這個項目的包,大家有需要可以下載來看一看,我是新手,有什麼不足之處歡迎大家交流,下載地址爲:
http://download.csdn.net/detail/a6627651/8617683