废话少说,游戏需要一个随机地图生成器,我就麻溜滚去搜索引擎找地图生成算法了。
最后从各种噪声算法里挑中一个Worley噪声,下图是此算法的效果示意。
选中这个算法主要就是一点:它能直接均匀稳定的生成块状区域,比较符合游戏的需要,算法的输出结果直接就能拿来用了。
看懂算法后,经过短暂的研究,我顺利实现了将不同区块标记编号。
思路很简单,Worley噪声这个算法本身就是在算距离场,那就把最近的**锚点作为key**存进map里,最后再把锚点key的索引转换成整型,就有了id。
至于染什么色(地表类型)基本根据区块id随机就好。
然后是边界的识别,我的选择是在搜索最小距离的锚点时,顺带求下 次最小距离 和最小距离的差值,如果小于指定阈值,那就判定为边界。最终效果我是够用了。
(不同分辨率下的简单染色图,黑色为边界,白点为锚点。可以看出高分辨率下的效果明显观感差了很多,要调整到合适的区间估计要做额外的很多工作,但我只需要低精度的地图,这里只贴出来看看样子)
(黑色为山顶、山脊,灰色是山坡,绿色是平原,蓝色是海平面以下的水,紫色是“神庙小岛”)
最后是二次处理,把锚点判定为最低点(特殊点:mc的神庙、boss点这种),把锚点周边一圈在更高的两个梯度间随机输出,再外面一圈升完梯度继续随机输出。
边界点周边和锚点进行一样的操作,只是梯度反过来。
(为了保证山脉的连续性和隔断效果,我选择了边界点周围一圈先于锚点输出)
另外把不在边界点和锚点辐射范围的地方按中间两个梯度随机输出,最后就成了染色图里的样子。
- PS:如果需要更细粒度更拟真的地形图,应该只需要根据每个点最近的边界和锚点平滑计算梯度。——虽然没有测试过,但结果想必是个标准的等高线地图。
- PS1:要避免锚点过于集中的话,可以把锚点的随机范围限定一个内边距。
- PS2:要避免锚点落在地图边缘的话,可以把锚点晶格的“画布”大小加个外边距。
- PS3:如果使用可控的伪随机来生成锚点,则能实现地图分块生成,不论是多线程还是懒加载都能支持了。这点必须高亮。
- PS4:如果需要更精细、连续的边界判定,生成完区块之后再计算区块内各个角度最远的点,如果有不连续的地方再把不连续的点从区块内部连起来就行了
- PS5:如果需要更多变(不只是凸多边形)的区块形状,找个办法把相邻的区块连起来就行了
- PS6:如果要生成像瓷砖那样可以无缝拼接的滚轴地图,只需要把超过地图画布左侧的锚点重定向为最右侧对应晶格的锚点,并把右侧越界锚点反过来操作就行了。
和voronoi有啥区别?
@林荫:好像是一个东西🤔?