【问题标题】:Generate Voronoi diagram without using Fortune's algorithm不使用 Fortune 算法生成 Voronoi 图
【发布时间】:2018-01-02 16:28:00
【问题描述】:

我希望用 C# 在 Unity 中创建 Voronoi 风景。我查看了许多 Unity Project 文件,但它们都实现了 Fortune 的算法,这完全超出了我的想象。还有其他生成Voronoi图的方法(更容易理解)吗? 缓慢的性能对我来说完全没问题。 非常感谢!


旁注:由于我在 Unity 中工作并且需要从 Voronoi 图生成 2D/3D 网格,因此每像素距离检查将不起作用 :,( 再想一想,也许我可以使用 Vector2s 的二维数组而不是像素,它们在 x 和 z 轴上间隔 1.0 个单位。

【问题讨论】:

  • 那么你真的需要几何精确的 Voronoi 图还是像素近似值,正如你提到的“风景”?
  • 近似值绝对没问题。虽然拥有顶点或边缘数据会很好,但我可以使用它们来生成网格。谢谢你!

标签: c# unity3d voronoi


【解决方案1】:

有一种非常简单的方法可以创建一个近似的 Voronoi 图 VD。对于应该在 VD(2D 平面)中定义一个单元格的每个站点 s,您将一个圆锥体居中在 s 处,具有恒定的坡度和一定的高度。然后你从上面看到锥体的景观(所有的尖峰都是可见的)。不同锥体相遇的边界(投影到 2D 平面)是(近似的)Voronoi 图。

(Image Source)

正如您在 cmets 中所要求的,获取实际的边缘数据似乎并不容易。但是可能有一些图形例程可以通过与锥体相交来生成它们。


另一种方法是计算给定点集的 Delaunay 三角剖分。这个related post 中引用了一些实现(也提到了简单的近似值)。然后计算三角剖分的对偶图,得到 Voronoi 图。 (对偶图意味着对于三角剖分中的每条边AB,VD 中存在一条边,将两个顶点AB 之间的空间一分为二,并且对于每个三角形,VD 中存在一个顶点,其中双边相遇。)另外还有很多C# Voronoi 实现:Unity-delaunay,但正如你提到的使用 Fortune 方法。


如果您想自己编写所有代码,您可以在 O(n^2) 时间用蛮力计算点的三角剖分 n 点。然后应用圈内测试和edge flips。也就是说,为每个三角形t(abc) 创建一个由t 的三个顶点定义的圆C。然后检查是否在C 中设置了另一个点d。如果是这样,则翻转t 中的边,并与d 形成三角形中的边。这种翻转一直进行到所有三角形都满足空圆属性(Delaunay 条件)。再次使用蛮力将花费O(n^2) 时间。然后你可以计算上面提到的对偶图。

(Image Source)

【讨论】:

  • @gui:你是博士?哇!
  • 这个想法是只放置锥体而不实际相交它们。然后,您可以使用任何光线追踪器(如 Blender),从顶部查看并立即“看到”(用人眼)VD,因为它是由锥体之间的山谷形成的。从下面你只会看到一个平坦的表面。从这个图形表示中得到实际的 VD 并不是那么简单。
【解决方案2】:

“最简单?这是蛮力方法:对于输出中的每个像素,遍历所有点,计算距离,使用最接近的点。虽然可能很慢,但非常简单。如果性能不重要,它确实如此这份工作。”

[1]Easiest algorithm of Voronoi diagram to implement?

【讨论】:

猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-04-08
  • 1970-01-01
相关资源
最近更新 更多