Ejemplo n.º 1
0
    /// <summary>
    /// 方法:寻路算法
    /// </summary>
    ///<param name="sg">起点</param>
    ///<param name="eg">终点</param>
    ///<param name="map">Map类的实例</param>
    ///<returns>PacGrid:返回路径起点</returns>
    internal PacGrid Find(PacGrid sg, PacGrid eg, PacMap map)
    {
        openList.Clear();
        closeList.Clear();
        openList.Add(sg);
        PacGrid g;
        int     i = 0;

        while (!IsInList(eg.X, eg.Y, openList) || openList.Count == 0)
        {
            g = GetMinFFromList(openList);
            if (g != null)
            {
                openList.Remove(g);
                closeList.Add(g);
                CheckAround(g, eg, map);
            }
            else
            {
                return(g);
            }
            i++;
        }
        PacGrid tmpg = GetGridFromList(eg, openList);

        return(Save(tmpg));
    }
Ejemplo n.º 2
0
 /// <summary>
 /// 方法:追击寻路
 /// </summary>
 private void Chase()
 {
     CurrentGrid = nextGrid;
     nextGrid    = LookAt(CurrentGrid, PacmanGrid);
     //if (nextGrid.sunGrid != null)
     //    nextGrid = nextGrid.sunGrid;
 }
Ejemplo n.º 3
0
    /// <summary>
    /// 方法:逃跑寻路
    /// </summary>
    private void Flee()
    {
        CurrentGrid = nextGrid;
        PacGrid gg = DodgePoint(CurrentGrid, PacmanGrid, SensingRange);

        nextGrid = LookAt(CurrentGrid, gg);
        //if (nextGrid.sunGrid != null)
        //    nextGrid = nextGrid.sunGrid;
    }
Ejemplo n.º 4
0
 /// <summary>
 /// 方法:怪物初始化
 /// </summary>
 private void EnemyReset()
 {
     dest     = BeginPoint.transform.position;
     dX       = (int)dest.x;
     dY       = (int)dest.y;
     nextGrid = new PacGrid()
     {
         X = dX, Y = dY
     };
 }
Ejemplo n.º 5
0
 /// <summary>
 /// 方法:寻找路径
 /// </summary>
 /// <param name="sg">寻路起点</param>
 /// <param name="eg">寻路终点</param>
 /// <returns>PacGrid:返回路径的起点</returns>
 private PacGrid LookAt(PacGrid sg, PacGrid eg)
 {
     ClearPath();
     sg.LandAttribute    = 1;
     mapSample.StartGrid = sg;
     eg.LandAttribute    = 1;
     mapSample.EndGrid   = eg;
     //寻路
     return(path.Find(mapSample.StartGrid, mapSample.EndGrid, mapSample));
 }
Ejemplo n.º 6
0
 /// <summary>
 /// 方法:对所有网格的地形属性进行初始化设置从而生成一张地图
 /// </summary>
 ///<param name="grid">当前节点</param>
 ///<param name="landform">地形选项</param>
 internal void MapGridSet(PacGrid grid, byte landform)
 {
     if (landform > landTypes)
     {
         return;
     }
     else
     {
         grid.LandAttribute = landform;
     }
 }
Ejemplo n.º 7
0
 /// <summary>
 /// 方法:从指定列表里获取指定节点
 /// </summary>
 ///<param name="grid">节点</param>
 ///<param name="list">列表</param>
 /// <returns>Grid:返回指定节点</returns>
 protected PacGrid GetGridFromList(PacGrid grid, List <PacGrid> list)
 {
     foreach (PacGrid g in list)
     {
         if (g.X == grid.X && g.Y == grid.Y)
         {
             return(g);
         }
     }
     return(null);
 }
Ejemplo n.º 8
0
    /// <summary>
    /// 方法:巡逻寻路
    /// </summary>
    private void Patrol()
    {
        CurrentGrid = nextGrid;
        //if (nextGrid.sunGrid != null)
        //    nextGrid = nextGrid.sunGrid;
        //else
        //{
        PacGrid gg = PatrolTarget(CurrentGrid, PatrolRange);

        nextGrid = LookAt(CurrentGrid, gg);
        //}
    }
Ejemplo n.º 9
0
    /// <summary>
    /// 方法:寻找巡逻范围内所有路径点
    /// </summary>
    /// <param name="sg">当前位置</param>
    /// <param name="gripMap">网格路径图</param>
    /// <param name="range">范围</param>
    /// <returns>List PacGrid :路径点集合</returns>
    private List <PacGrid> isInRange(PacGrid sg, PacGrid[,] gripMap, int range)
    {
        List <PacGrid> gripPath = new List <PacGrid>();

        foreach (PacGrid g in gripMap)
        {
            if (g.LandAttribute == 1 && GetDistance(sg, g) < range)
            {
                gripPath.Add(g);
            }
        }
        return(gripPath);
    }
Ejemplo n.º 10
0
    /// <summary>
    /// 方法:保存路径
    /// </summary>
    ///<param name="g">节点</param>
    internal PacGrid Save(PacGrid g)
    {
        PacGrid TransGrid;

        while (g.fatherGrid != null)
        {
            g.PathAttribute = true;
            TransGrid       = g;
            g         = g.fatherGrid;
            g.sunGrid = TransGrid;
        }
        return(g);
    }
Ejemplo n.º 11
0
    /// <summary>
    /// 方法:巡逻范围内寻找躲避点
    /// </summary>
    /// <param name="sg">当前位置</param>
    /// <param name="Target">目标位置</param>
    /// <param name="range">巡逻范围</param>
    /// <returns>PacGrid:躲避点</returns>
    private PacGrid DodgePoint(PacGrid sg, PacGrid Target, int range)
    {
        List <PacGrid> gripPath = isInRange(sg, gripMap, range);
        PacGrid        rg       = gripPath[0];

        foreach (PacGrid g in gripPath)
        {
            if (GetDistance(Target, g) > GetDistance(Target, rg))
            {
                rg = g;
            }
        }
        return(rg);
    }
Ejemplo n.º 12
0
 /// <summary>
 /// 方法:计算G耗费
 /// </summary>
 ///<param name="x">坐标x</param>
 ///<param name="y">坐标y</param>
 ///<param name="sg">起点</param>
 /// <returns>Int:G值</returns>
 protected int GetGridCostG(PacGrid CurrentGrid, PacGrid sg)
 {
     //if (CurrentGrid.fatherGrid != null)
     //    return (sg.X == CurrentGrid.X || sg.Y == CurrentGrid.Y) ? CurrentGrid.fatherGrid.GCostAttribute + 10 : CurrentGrid.fatherGrid.GCostAttribute + 21;
     //else
     //    return 0;
     if (CurrentGrid.fatherGrid != null)
     {
         return((sg.X == CurrentGrid.X || sg.Y == CurrentGrid.Y) ? sg.GCostAttribute + 10 : sg.GCostAttribute + 14);
     }
     else
     {
         return(0);
     }
 }
Ejemplo n.º 13
0
 /// <summary>
 /// 构造方法:初始化地图
 /// </summary>
 ///<param name="x">地图长</param>
 ///<param name="y">地图宽</param>
 public PacMap(int x, int y)
 {
     LenX      = x;
     LenY      = y;
     simpleMap = new PacGrid[LenX, LenY];
     for (int i = 0; i < LenX; i++)
     {
         for (int j = 0; j < LenY; j++)
         {
             simpleMap[i, j] = new PacGrid()
             {
                 X = i, Y = j
             };
         }
     }
 }
Ejemplo n.º 14
0
    /// <summary>
    /// 方法:从指定列表中获取F值最小的节点
    /// </summary>
    ///<param name="list">列表</param>
    /// <returns>Grid:F值最小的节点</returns>
    protected PacGrid GetMinFFromList(List <PacGrid> list)
    {
        PacGrid rg = new PacGrid();

        if (list.Count == 0)
        {
            return(null);
        }
        rg = list[0];
        //int tmpF = list[0].GCostAttribute + list[0].HCostAttribute;
        foreach (PacGrid g in list)
        {
            if (g.GCostAttribute + g.HCostAttribute < rg.GCostAttribute + rg.HCostAttribute)
            {
                rg = g;
            }
        }
        return(rg);
    }
Ejemplo n.º 15
0
    /// <summary>
    /// 方法:路径记忆清除
    /// </summary>
    private void ClearPath()
    {
        PacGrid bg;

        while (nextGrid.sunGrid != null)
        {
            nextGrid = nextGrid.sunGrid;
        }

        while (nextGrid.fatherGrid != null)
        {
            bg            = nextGrid;
            nextGrid      = nextGrid.fatherGrid;
            bg.fatherGrid = null;
        }
        while (nextGrid.sunGrid != null)
        {
            bg         = nextGrid;
            nextGrid   = nextGrid.sunGrid;
            bg.sunGrid = null;
        }
    }
Ejemplo n.º 16
0
    /// <summary>
    /// 方法:检查当前节点周边的节点
    /// </summary>
    ///<param name="sg">当前节点</param>
    ///<param name="eg">终点</param>
    ///<param name="map">Map类的实例</param>
    protected void CheckAround(PacGrid sg, PacGrid eg, PacMap map) //
    {
        int gridmapRow = map.LenY;                                 //获取地图的行数
        int gridmapCol = map.LenX;                                 //获取地图的列数

        PacGrid[,] gridmap = map.simpleMap;
        for (int i = sg.X - 1; i < sg.X + 2; i++)
        {
            for (int j = sg.Y - 1; j < sg.Y + 2; j++)                           //筛选出相邻点
            {
                if (i < 0 || i > gridmapCol - 1 || j < 0 || j > gridmapRow - 1) //若超出地图,pass
                {
                    continue;
                }
                if (gridmap[i, j].LandAttribute == 0 || IsInList(i, j, closeList) || (i == sg.X && j == sg.Y))//若为障碍点/已考虑节点/当前点,pass
                {
                    continue;
                }
                gridmap[i, j].HCostAttribute = GetGridCostH(i, j, eg);              //计算H值(此节点到目标节点的移动损耗)
                if (!IsInList(i, j, openList))                                      //不在open列表,则加入
                {
                    openList.Add(gridmap[i, j]);                                    //加入open列表
                    gridmap[i, j].fatherGrid     = sg;                              //将此节点的父节点设为当前节点
                    gridmap[i, j].GCostAttribute = GetGridCostG(gridmap[i, j], sg); //计算G值(从起点到此节点的移动损耗)
                }
                else
                {
                    int k = GetGridCostG(gridmap[i, j], sg);
                    if (gridmap[i, j].GCostAttribute > k)  //如果此节点经由当前节点离起点更近,则指向当前节点
                    {
                        gridmap[i, j].GCostAttribute = k;  //更新G值
                        gridmap[i, j].fatherGrid     = sg; //更新父节点
                    }
                }
            }
        }
    }
Ejemplo n.º 17
0
 /// <summary>
 /// 方法:计算H耗费
 /// </summary>
 ///<param name="x">坐标x</param>
 ///<param name="y">坐标y</param>
 ///<param name="eg">终点</param>
 /// <returns>Int:H值</returns>
 protected int GetGridCostH(int x, int y, PacGrid eg)
 {
     return(Math.Abs(x - eg.X) + Math.Abs(y - eg.Y));
 }
Ejemplo n.º 18
0
 /// <summary>
 /// 方法:计算两个格子的路程
 /// </summary>
 /// <param name="sg">起点</param>
 /// <param name="eg">终点</param>
 /// <returns>int:距离</returns>
 protected int GetDistance(PacGrid sg, PacGrid eg)
 {
     return((int)Math.Abs(sg.X - eg.X) + (int)Math.Abs(sg.Y - eg.Y));
 }
Ejemplo n.º 19
0
    /// <summary>
    /// 方法:固定频率执行
    /// </summary>
    private void FixedUpdate()
    {
        if (transform.position != PacMan.transform.position && enemyStatus != EnemyStatus.Still)
        {
            if (isReset == false)
            {
                Vector2 temp = Vector2.MoveTowards(transform.position, dest, PacManSpeed);
                enemyRigidbody2d.MovePosition(temp);

                if ((Vector2)transform.position == dest)
                {
                    if (dest.x == dX && dest.y == dY)
                    {
                        if (nextGrid.sunGrid != null)
                        {
                            nextGrid = nextGrid.sunGrid;
                        }
                        else
                        {
                            //PacGrid gg = PatrolTarget(nextGrid, PatrolRange);
                            //nextGrid = LookAt(nextGrid, gg);
                            CarryOut(enemyStatus);
                        }
                        dX = nextGrid.X;
                        dY = nextGrid.Y;

                        if (gripMap[dX, dY].LandAttribute != 0)
                        {
                            dest = new Vector2(dX, dY);
                        }
                    }
                    if (isChase == true)
                    {
                        if (GetDistance(nextGrid, PacmanGrid) <= SensingRange)
                        {
                            enemyStatus = EnemyStatus.Chase;
                        }
                        else
                        {
                            enemyStatus = EnemyStatus.Patrol;
                        }
                    }
                }
                Vector2 dir = dest - (Vector2)transform.position;
                GetComponent <Animator>().SetFloat("DirX", dir.x);
                GetComponent <Animator>().SetFloat("DirY", dir.y);
            }
            else
            {//归元
                isReset = false;
                EnemyReset();
            }
        }

        PacmanGrid = new PacGrid()
        {
            X = (int)PacMan.transform.position.x, Y = (int)PacMan.transform.position.y
        };


        if (LastEnemyStatus != enemyStatus)
        {
            CarryOut(enemyStatus);
        }
        LastEnemyStatus = enemyStatus;
    }
Ejemplo n.º 20
0
    /// <summary>
    /// 方法:巡逻范围内随机寻点
    /// </summary>
    /// <param name="sg">当前位置</param>
    /// <param name="range">巡逻范围</param>
    /// <returns>PacGrid:寻找到的随机点</returns>
    private PacGrid PatrolTarget(PacGrid sg, int range)
    {
        List <PacGrid> gripPath = isInRange(sg, gripMap, range);

        return(gripPath[UnityEngine.Random.Range(0, gripPath.Count) - 1]);
    }