因为游戏初步定为塔防类型,所以这里需要个简单的寻路算法,玩法对寻路效率要求并不高,所以就实现了个最简单的寻路算法

1.只能上下左右走

2.未做任何优化,可优化空间较大

3.初步测试, 15*15格子 什么都不摆 耗时 2 毫秒 (a*算法在没有障碍物的情况下基本上要遍历所有的路径,所以在这种情况下是最耗时的)

(蓝:start 绿:end 红:障碍 黄:路径)

代码如下,注释较多,有问题可以留言,代码文件可以直接拿到自己工程里使用

XXAStar = {}local function removeChild(parent,child) --table 删除子local list = parentfor k,v in pairs(list) doif v == child thentable.remove(list,k)return listendend
end
local function getRoundPos(pos,closeList,openList) --寻找周围合法点,不在open 也不在closelocal px = pos.xlocal py = pos.ylocal list = {{x=px ,y=py+1},     --上{x=px-1 ,y=py},        --左{x=px+1    ,y=py},        --右{x=px   ,y=py-1},  --下}local returnList = {}for _,v in pairs(list) doif v.x >= 1 and v.y >= 1 then --地图范围内if v.x <= XXAStar.size.width and v.y <= XXAStar.size.height thenif closeList[v.x][v.y] == 0 then --排除closelistlocal isInOpen = nilfor _,v1 in pairs(openList) do  --排除open列表if v1.x == v.x and v1.y == v.y thenisInOpen = v1endendif isInOpen == nil thentable.insert( returnList,v )else --如果在open中 需要更新查看F是否更小local newG = pos.g + (math.abs(pos.x - v.x) + math.abs(pos.y - v.y) )if newG < isInOpen.g thenisInOpen.parent = posisInOpen.g = newGendendendendendendreturn returnList
end
local function countFGH(startpos,endpos,list) --计算 FGH--  G = 从 起点   移动到 指定点--  H = 从 指定点 移动到 终点--  F = G + Hlocal minF = nilfor _,v in pairs(list) doif v.g == nil thenv.g = math.abs(startpos.x - v.x) + math.abs(startpos.y - v.y)v.h = math.abs(v.x - endpos.x) + math.abs(v.y - endpos.y)v.f = v.g+v.hendif minF == nil thenminF = vendif v.f < minF.f thenminF = vendendreturn minF
end
function XXAStar:init()--寻路二维数组self.size = {width=0,height=0}    --尺寸self.pathList = {}                 --路径数据self.startPos = nil              --起始点self.endPos = nil             --终止点self.openList = {}                self.closeList = {}
end
function XXAStar:getPath(width,height,startpos,endpos,closeList)--初始化self:init()self.size.width = widthself.size.height = heightfor j=1,width,1 doself.pathList[j] = {}self.closeList[j] = {}for i=1,height,1 doself.pathList[j][i] = { type = 0 }self.closeList[j][i] = 0endendself.startPos = startposself.endPos = endpos--1.起始点加入到open列表中table.insert(self.openList,self.startPos)--2.将障碍物放到close列表for k,v in pairs(closeList) doself.pathList[v.x][v.y].type = 1self.closeList[v.x][v.y] = 1end--8.回溯路径local resultList = {}local lastPos = self:countPath(self.startPos)if lastPos == nil then return {}endwhile(true)doif lastPos.parent == nil thenbreakendif lastPos.parent.x == self.startPos.x and lastPos.parent.y == self.startPos.y thenbreakendtable.insert( resultList,{x=lastPos.parent.x,y=lastPos.parent.y} )lastPos = lastPos.parentendreturn resultList
end
function XXAStar:countPath( firstPos )--3.根据起点寻找周围相邻点,排除障碍物local roundlist = getRoundPos(firstPos,self.closeList,self.openList)--4.把起点从openlist中移除,加入到closelistself.openList = removeChild(self.openList,firstPos)self.closeList[firstPos.x][firstPos.y] = firstPos--5.找到的点加入到openlistfor _,v in pairs(roundlist) dov.parent = firstPostable.insert(self.openList,v)--6 查看是否找到了终点if v.x == self.endPos.x and v.y == self.endPos.y thenreturn vendend--7.计算 FGH 并得到f最小的值local minF = countFGH(self.startPos,self.endPos,self.openList)if minF == nil then--已经没有未遍历的点了return nilelsereturn self:countPath(minF)end
end

使用示例:

--[[
function XXAStar:getPath(width,height,startpos,endpos,closeList)
--width,height    尺寸
--startpos        起始点
--endpos          终止点
--closeList       障碍物
]]--local usePosList = XXAStar:getPath(15,15,{x=1,y=1},{x=15,y=15},closeList)
if table.getn(usePosList) == 0 thenXXLog("没有找到路径")
else--TODO--usePosList 路径的坐标点集合
end

游戏开发(十) 之 lua 150行代码 实现A*寻路相关推荐

  1. 游戏开发学习笔记——lua脚本语言——安装、汉化与小测试(解决lua运行代码乱码问题)

    游戏开发学习笔记--lua脚本语言--安装.汉化与小测试 FOR THE SIGMA FOR THE GTINDER FOR THE ROBOMASTER 简介: Lua 是一种轻量小巧的脚本语言,用 ...

  2. hash签名 java_java开发区块链只需150行代码

    原标题:java开发区块链只需150行代码 本文帮助你理解什么是区块链.将通过java开发区块链的实战学习方式,用 Java创建开发一个基本的区块链,实现简单的工作量证明系统.Java开发区块链的源代 ...

  3. 【线程池】自行准备linux环境,带你手写线程池,只需仅仅150行代码|内存池|API|连接池|应用协议丨C/C++Linux服务器开发

    [线程池]自行准备linux环境,带你手写线程池,只需仅仅150行代码 视频讲解如下,点击观看: [线程池]自行准备linux环境,带你手写线程池,只需仅仅150行代码|内存池|API|连接池|应用协 ...

  4. android 用代码模拟滑动,Android开发之使用150行代码实现滑动返回效果

    今天带大家实现滑动返回效果.,具体内容如下所示: 先看看效果图: 因为没有具体内容,也没有简书的图片资源,所以稍微简陋了点. 但是依然不妨碍我们的效果展示~ OK,接下来惯例,通过阅读本文你能学习到: ...

  5. 【ANDROID游戏开发十六】ANDROID GESTURE之【触摸屏手势识别】操作!利用触摸屏手势实现一个简单切换图片的功能!...

    本站文章均为 李华明Himi 原创,转载务必在明显处注明: 转载自[黑米GameDev街区] 原文链接: http://www.himigame.com/android-game/337.html - ...

  6. HTML5游戏开发(十)

    HTML5游戏开发(十) 一.动画 1.动画循环   在Canvas中这病动画效果很简单:只需要在播放动画时持续更新并绘制就行了.这种持续更新与重绘叫就动画循环. (1)通过requestAnimat ...

  7. Android游戏开发十日通(7)- 开发一个双人游戏

    提要 游戏需要分享才能获得快乐,想想你以前玩过的那些游戏,那些会是真正地存在你婶婶的脑海里?是独自一人躲在被窝里酣战PSP,还是和哥们在网吧一起开黑?是一个人单刷迅龙三连,还是和朋友联机怒刷黄黑龙? ...

  8. APP游戏开发十诫!第一个雏型就要搞定的事

    APP游戏开发十诫!第一个雏型就要搞定的事 半路:在启动游戏 App 项目时,多数开发者都能条列出上百项的重要功能,似乎每个项目都非得完成不可,但到底哪些才是项目早期至关紧要,必须在第一个游戏雏型完成 ...

  9. 【线程池】自行准备linux环境,带你手写线程池,只需仅仅150行代码

    [线程池]自行准备linux环境,带你手写线程池,只需仅仅150行代码 视频讲解如下,点击观看: [线程池]自行准备linux环境,带你手写线程池,只需仅仅150行代码|内存池|API|连接池|应用协 ...

最新文章

  1. 随记:kickstart远程批量无人值守安装linux
  2. 普林斯顿算法(1.3)并查集(union-find算法)——本质就是一个数 下面的子树代表了连在一起的点...
  3. java 静态成员不能调用 非静态成员_为什么静态成员不能访问非静态成员
  4. winform 转 JAVA_C#转java
  5. 数据库面试题【十三、大表数据查询,怎么优化】
  6. 操作系统--内核级线程实现
  7. 使用 position: sticky 达到粘性元素区域悬浮效果
  8. kettle系列-6.kettle实现多字段字典快速翻译
  9. php pcre回溯攻击,PHP利用PCRE回溯次数限制绕过某些安全限制 | 码农网
  10. Python 3.9.0a6 已可用于测试
  11. Git 出现Branch master set up to track remote branch master问题 与忽略文件上传
  12. vue 初始化请求例子_Vue实例初始化
  13. SAP程序下载模板显示异常问题解析
  14. SPSS Statistics 分位数回归 翻译文档
  15. 引用百度地图,隐藏百度地图logo
  16. 智遥工作流为Sap报工时(实例)
  17. B05 - 008、什么是大数据
  18. 汇编语言里 eax, ebx, ecx, edx, esi, edi, ebp, esp 寄存器 含义
  19. 最有效的赚钱方法,只有100元如何赚到10万?
  20. php 腾讯云 文字识别_讯飞语音转文字,图片转文字,效率高还免费

热门文章

  1. Discuz常用知识点总结
  2. GO005:转义字符
  3. 不止是“平替” | 从统信技术开放日看国产OS“乾坤大挪移”
  4. GIS开发:Vector tiles切片工具
  5. XHProf Documentation (XHProf 中文手册)
  6. 贵阳大数据交易所推“数据星河”等十大战略
  7. 面试 技术 教训_我在30天内进行60多次技术面试的经验教训
  8. openstack-havana记录一下。。。
  9. (附源码)Springboot电子病历管理 毕业设计 010350
  10. python中的shape[-1]与shape[0],shape[1]的含义,用法