【问题标题】:Vector graphics flood fill algorithms?矢量图形洪水填充算法?
【发布时间】:2011-08-16 15:21:18
【问题描述】:

我正在开发一个简单的绘图应用程序,我需要一种算法来进行洪水填充。
用户工作流程将如下所示(类似于 Flash CS,只是更简单):

  1. 用户在工作区绘制直线。这些被视为矢量,绘制后可以选择和移动。
  2. 用户选择填充工具,然后单击绘图区域。如果该区域被各个方向的线包围,则对该区域应用填充。

如果在应用填充后移动线条,则填充区域会相应更改。

任何人都有一个好主意,如何实现这样的算法?主要任务基本上是确定一个点周围的线段。 (并以某种方式存储这些信息,以防线条被移动)

编辑:解释图像:(画布中当然可以有其他线条,这与填充算法无关)

EDIT2:更困难的情况:

EDIT3:我找到了一种用孔填充多边形的方法http://alienryderflex.com/polygon_fill/,现在主要问题是,我如何找到我的多边形?

【问题讨论】:

  • 我在想某种递归蛮力算法。从附近的一条线开始并递归到它重叠的线,直到你回到第一条线。
  • “递归到它重叠的行”是什么意思?递归函数是做什么的?
  • 对不起,我倾向于在这里阅读人们的 cmets。它经常适得其反。
  • @sydd 结果填充需要是矢量还是位图?
  • @Nitesh 我得到了 hvidgaard 正在谈论的书,并实现了那里描述的点定位器算法。请注意,图形表示 (DCEL) 和用于存储点的数据结构与算法本身一样重要。 Actionscript afaik 中没有开源实现,但我可能会在某个时候开源我的。

标签: actionscript-3 language-agnostic geometry vector-graphics flood-fill


【解决方案1】:

您正在寻找一种点定位算法。它并不过分复杂,但在这里解释起来也不够简单。这本书里有一个很好的章节:http://www.cs.uu.nl/geobook/

当我回到家时,我会拿到我的那本书,看看我是否可以尝试。您需要了解的只是很多细节。这一切都归结为构建输入的 DCEL 并在添加或删除行时维护数据结构。任何带有鼠标坐标的查询都只会返回组件的内部半边,特别是那些包含指向所有内部组件的指针,这正是您所要求的。

但有一件事是你需要知道输入中的交叉点(因为如果你有相交的线,你就无法构建梯形地图),如果你能逃脱它(即输入是足够少的段)我强烈建议您只使用简单的 O(n²) 算法(简单、可编码和可在不到 1 小时内测试)。 O(n log n) 算法需要几天时间来编码并使用一个聪明且非常重要的数据结构来表示状态。然而,书中也提到了它,所以如果你觉得能胜任这项任务,你有两个理由购买它。总的来说,这是一本关于几何问题的非常好的书,因此任何对算法和数据结构感兴趣的程序员都应该拥有一本。

【讨论】:

  • 非常感谢,这似乎是一个很好的解决方案。不会有那么多行,所以我认为朴素算法会起作用。
  • DCEL:双连通边列表?
【解决方案2】:

试试这个:

http://keith-hair.net/blog/2008/08/04/find-intersection-point-of-two-lines-in-as3/

该函数返回 ActionScript 中两行之间的交点(如果有)。您需要循环遍历所有行,以获取所有行。

当然,如果您打算填写积分,那么积分的顺序会很重要 - 这可能会更难!

【讨论】:

  • @oliver-emberton 我认为这种方法行不通,您如何找到要填充的区域内的闭合形状? (我添加了一个例子)
  • @sydd - 你是对的,我提交的所有代码都是找到线之间的相交坐标。确定其中的形状更复杂 - 我没有直接的解决方案。
【解决方案3】:

借助 ActionScript,您可以使用 beginFillendFill,例如

pen_mc.beginFill(0x000000,100);
pen_mc.lineTo(400,100);
pen_mc.lineTo(400,200);
pen_mc.lineTo(300,200);
pen_mc.lineTo(300,100);
pen_mc.endFill();

http://www.actionscript.org/resources/articles/212/1/Dynamic-Drawing-Using-ActionScript/Page1.html

Flash CS4 还引入了对路径的支持:

http://www.flashandmath.com/basic/drawpathCS4/index.html

如果您想发疯并编写自己的洪水填充代码,那么维基百科有一个 decent primer,但我认为这将是为了这些目的而重新发明原子。

【讨论】:

  • 我的问题不是填充,而是如何确定要填充的区域的边界。我将制作一个示例图像
  • @sydd - 所以你正在寻找线条相交的地方,然后在里面填充?图片会有所帮助,谢谢。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2014-05-29
  • 2014-02-16
  • 1970-01-01
  • 1970-01-01
  • 2015-11-19
相关资源
最近更新 更多