Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/design-patterns/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 将网格转换为用于导航的图形_C#_Algorithm_Unity3d_Path Finding_Navmesh - Fatal编程技术网

C# 将网格转换为用于导航的图形

C# 将网格转换为用于导航的图形,c#,algorithm,unity3d,path-finding,navmesh,C#,Algorithm,Unity3d,Path Finding,Navmesh,旁注:我不确定这个问题是否属于游戏开发堆栈交换站点——但是,我觉得它属于这里,因为虽然上下文是一个游戏,但我希望实现的算法本身与应用程序无关。此外,我不是在寻找一种高水平的技术,因为我觉得我已经建立了一种技术,而是在寻求针对某个问题的更具体的帮助。无论如何,对于这个问题: 大家好 我正在开发一个多人游戏,它要求服务器可以为服务器控制的实体执行路径查找。服务器是一个直接的C#应用程序,客户端使用Unity游戏引擎。在服务器上使用Unity不是一个选项。此外,我希望完全避免使用本机库 我已经检查了寻

旁注:我不确定这个问题是否属于游戏开发堆栈交换站点——但是,我觉得它属于这里,因为虽然上下文是一个游戏,但我希望实现的算法本身与应用程序无关。此外,我不是在寻找一种高水平的技术,因为我觉得我已经建立了一种技术,而是在寻求针对某个问题的更具体的帮助。无论如何,对于这个问题:

大家好

我正在开发一个多人游戏,它要求服务器可以为服务器控制的实体执行路径查找。服务器是一个直接的C#应用程序,客户端使用Unity游戏引擎。在服务器上使用Unity不是一个选项。此外,我希望完全避免使用本机库

我已经检查了寻路的迂回路线,虽然它们确实有C#Port,但我更希望有自己的实际寻路位实现;因为这个过程非常简单,我希望它能够根据我的需要进行定制,以便与服务器上现有的组件配合使用

Unity内置了对重铸/迂回的支持。这很好,因为我可以在Unity中使用重铸来生成导航网格;然后使用我自己的路径查找在服务器上使用它。问题是,我似乎找不到一个合适的方法来根据Unity/Recast创建的网格生成图形

我需要做的是在内存中创建一个图,其中每个节点是网格中的一个三角形,图的每条边连接两个相邻的三角形

我能够从Unity的API中提取的唯一数据是生成网格的顶点和三角形索引,因此我需要重新构建自己的图形。我的第一个实现只是为每个三角形创建一个节点,如果该三角形与另一个三角形共享另外两个点,则在它们之间创建一个链接,形成图形的边

虽然这对大多数网格非常有效,但它的不足之处在于,Unity似乎正在吐出在区域(多边形)之间具有连接(边)的网格,即使它们不共享两个顶点。下面是Unity将其生成的navmesh覆盖到我的级别几何体上的示例(Unity确实将三角形合并为凸多边形,而我的代码没有-但是,在这两种情况下问题仍然存在)

在本例中,生成的图形需要连接由白线分隔的多边形(我找不到任何文档来解释为什么它在Unity中呈现为白色),但无法这样做,因为它们只共享一个顶点

我想知道是否有一个有效的算法来检测这些病例。我想做的是使多边形被认为是连通的:

if (sharedVertexCount == 2)
    connectPolygons()
else if (sharedVertexCount == 1)
    Vector3[] parallelLine = findParallelLineSharedByBothPolygons()
    if (parallelLine != null)
        Vector3 otherPoint = getUnsharedPointInLine(parallelLine)
        if (isPointInLine(parallelLine, otherPoint))
            connectPolygons()
我认为这应该行得通,但我没有找到有效的方法。此外,我在“isPointInLine”实现方面遇到了一些问题,因为我的数学技能显然比我想象的要粗糙


无论哪种方式,都必须有一个更简单的解决方案;然而,我在网上找不到任何东西能指引我走向那个方向。。。这就是为什么我要问大家,我能做些什么来有效地将生成的navmesh转化为连接多边形的图形。无论是帮助我实现isPointInLine,还是为我指明一个更合理的算法方向,都会让我感激不尽。

说到寻路,大多数方法都建议使用一种预制的数据结构,专门用于导航,更易于使用(除非你的图形数据结构足够简单——这里不是)

我建议你几种解决方案:

  • 基于体素的导航系统:实现一个具有三维布尔数组(不能通过)的体素系统,并在其上应用和一个星D星算法

  • 知道AI可以通过的路径向量

  • 两个系统的合并(主路径使用已知路径向量,而网格用false标记相交的体素。-这可能是您正在寻找的解决方案。


如果我正确理解了您的问题,基于可见性图的路径规划算法可以帮助:

线索是从现有的多边形地图中提取一个图,在该地图中,当节点彼此可以直接访问时,节点是连接在一起的。由此产生的所谓可见性图(cf.)可以用于常规最短路径算法的导航()

有很多现有算法可以有效地提取路径规划的可见性图。以下是一些相关链接:


好吧,我当然可以放弃Unity使用的重铸,编写自己的自动navmesh生成器;但是,由于从Unity的navmesh导出的三角形,我已经非常接近于有一个正在工作的实现,使用它作为我的寻路系统的输入。基本上,你是说这种方法不值得麻烦吗?这种方法对于大多数应用(游戏等),它是密封的你不需要一个气密的解决方案,你需要一个工作简单的可维护的解决方案。我是软件基础设施设计师,我喜欢气密的解决方案。lol…D*已经过时了,如果你真的需要它,你应该用D*-Lite来代替。然而,即使是D*-Lite对于游戏来说也是非常罕见的,因为它比a*复杂得多。更多信息请参阅信息。