您的位置:首页 > 其它

自动寻路方案

2015-07-01 18:56 369 查看
这里是用cube模拟的自动寻路。还不是最优的寻路方案



using UnityEngine;
using System.Collections;
using System.Collections.Generic;

class Point //代表人
{
public int X { get; set; }
public int Y { get; set; }

public Point Parent { get; set; }

public Point(int x, int y)
{
X = x;
Y = y;
}
}

public class ANavition : MonoBehaviour
{

List<Point> nowList; //正在访问的集合 讲台
List<Point> visitendList; //已经访问过的集合 ,白板

//玩家和目标
GameObject player;
GameObject target;

bool canReach; //能否到达目标点

bool[,] maps; //地图 二维数组

int[,] dir = new int[,] { { 0, 1 }/*up*/, { 0, -1 }/*down*/, { -1, 0 }/*left*/, { 1, 0 }/*right*/ };

Vector3 moveDir; //玩家自动寻路的方向

// Use this for initialization
void Start()
{
LoadGameMap();
InitGameMap();
FindTarget();

}

void OnGUI()
{
if (GUILayout.Button("刷新"))
{
Application.LoadLevel("03ANav");
}
}

// Update is called once per frame
void Update()
{
if (canReach)
{
AntoMove();
}
}

/// <summary>
/// 角色自动导航
/// </summary>
private void AntoMove()
{
if (ways.Count > 0)
{
moveDir = (ways.Peek() - player.transform.position).normalized;

player.transform.Translate(moveDir * Time.deltaTime);

//
if (Vector3.Distance(ways.Peek(), player.transform.position) < 0.1f)
{
ways.Pop();//弹出栈顶元素
}
}
}

/// <summary>
/// 找目标
/// </summary>
void FindTarget()
{
//初始化集合
nowList = new List<Point>();
visitendList = new List<Point>();

Point yangbo = new Point(0, 0);
//yangbo.X = 0;
//yangbo.Y = 0;

nowList.Add(yangbo);
visitendList.Add(yangbo);

Point first;
int x, y;
//只要有人,游戏一直继续玩下去
while (nowList.Count > 0)
{
first = nowList[0];

//dir-> 前 (0,1) 后(0,-1)
for (int i = 0; i < 4; i++)
{
x = first.X + dir[i, 0]; //第i个方向的x
y = first.Y + dir[i, 1]; //第i个方向的y

if (IsOk(x, y))
{
Point person = new Point(x, y);
person.Parent = first;

nowList.Add(person);//上讲台
visitendList.Add(person); //写上名字
}

//找到了目标点
if (IsFindTarGet(first))
{
break;
}
}

nowList.Remove(first); //移除上了讲台的人
}
}
Stack<Vector3> ways; //栈,存路径
bool IsFindTarGet(Point person)
{
if (person.X == 5 && person.Y == 5)
{
ways = new Stack<Vector3>();
while (person.Parent != null) //链表查找父亲
{
Vector3 pos = new Vector3(person.X, 1, person.Y);

ways.Push(pos);

person = person.Parent;
}
canReach = true;
return canReach;
}
return false;
}

bool IsOk(int x, int y)
{
//数组越界
if (x < 0 || y < 0 || x > 5 || y > 5) return false;

//访问过的节点不能再次访问
foreach (Point p in visitendList)
{
if (p.X == x && p.Y == y) return false;
}

return maps[x, y];
}

/// <summary>
/// 生成游戏地图数组
/// </summary>
public void LoadGameMap()
{
maps = new bool[6, 6]; //6行6列的游戏地图

for (int i = 0; i < maps.GetLength(0); i++)
{
for (int j = 0; j < maps.GetLength(1); j++)
{
//70% true  30% false
maps[i, j] = Random.Range(1, 11) <= 7 ? true : false;
}
}

//都必须是绿色 即为true
maps[0, 0] = true; //玩家起点位置
maps[5, 5] = true; //目标点位置
}

/// <summary>
/// 初始化地图
/// </summary>
void InitGameMap()
{
for (int i = 0; i < 6; i++)
{
for (int j = 0; j < 6; j++)
{
GameObject cube = GameObject.CreatePrimitive(PrimitiveType.Cube);
//cube.transform.position = new Vector3(j, i, 0);

cube.transform.position = new Vector3(i, 0, j); //从顶部看  xz平面上

//true为绿色。即可以走。false为红色。即不可以走
cube.transform.renderer.material.color = maps[i, j] ? Color.green : Color.red;

cube.transform.localScale = Vector3.one * 0.8f; //缩放cube

cube.transform.SetParent(transform); //设置父对象,便于管理
}
}

//玩家和目标
player = GameObject.CreatePrimitive(PrimitiveType.Capsule);

target = GameObject.CreatePrimitive(PrimitiveType.Sphere);

player.transform.position = new Vector3(0, 1, 0); //玩家的初始位置

player.transform.localScale = Vector3.one * 0.5f; //缩放玩家

target.transform.position = new Vector3(5, 1, 5); //目标点的位置

}

}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: