C# 正确拆分System.Windows.Media.PathGeometry

C# 正确拆分System.Windows.Media.PathGeometry,c#,wpf,geometry,.net-4.5,pathgeometry,C#,Wpf,Geometry,.net 4.5,Pathgeometry,我有一个System.Windows.Media.PathGeometry,如下所示: 我想分割几何体,这样每个灰色的形状都在一个新的几何体对象中。我曾尝试迭代PathGeometry的FigureCollection并将每个图形放入新的几何图形中,但结果与我预期的不同,因为一个图形只描述形状的一条边,而不是形状本身。这意味着,有些数字是加法的,有些是减法的: 为了正确分割几何图形,我必须弄清楚哪些路径图形是加法的,哪些是减法的。PathFigure类型上没有提供有关如何应用它的信息的属性。 有

我有一个System.Windows.Media.PathGeometry,如下所示: 我想分割几何体,这样每个灰色的形状都在一个新的几何体对象中。我曾尝试迭代PathGeometry的FigureCollection并将每个图形放入新的几何图形中,但结果与我预期的不同,因为一个图形只描述形状的一条边,而不是形状本身。这意味着,有些数字是加法的,有些是减法的: 为了正确分割几何图形,我必须弄清楚哪些路径图形是加法的,哪些是减法的。PathFigure类型上没有提供有关如何应用它的信息的属性。 有人知道如何解决这个问题吗


提前感谢。

如您所述,如果
路径图
不相交,即包含已完成,则推论是如果
路径图
A包含B,则A的AABB边界也包含B的AABB边界

不幸的是,我不认为
PathFigure
具有这样的属性,因此克服这一问题的一种方法可能是从
.Figures
属性内的每个
PathFigure
对象创建单个新的
PathGeometry
对象,并将其存储在数组中。然后使用
.Bounds.Contains
属性(即this:)对该数组进行排序,以代替常规排序例程中的比较操作


现在,您有了一个“Matryoshka玩偶”列表,其中包含
路径几何体
,从最外层开始,选择每一对连续的玩偶,并取其并集(
。如您所说,合并
)。如果数组的元素数为奇数,即最后只剩下一个,则图4中的情况必须如此

我目前也在尝试做同样的事情,下面是我的计划,以及一些思考过程

首先,将所有内容转换为PathGeometrics。
FillContains(Geometry)
方法是我想用来查看what的内部。包含<<代码>的问题是,如果你有一个C形状,中间有一个点,那么点将包含在包围矩形中,而不是形状。

接下来,创建一个树数据结构。如果PathGeometry A包含PathGeometry B,则A将是树中B的祖先。这里的另一个答案建议使用一个列表,但这不起作用。这一段的其余部分解释了原因。假设有两个PathFigure,其中一个都不在另一个内:对列表进行排序后,我们会假设其中一个在另一个内。我们可以不用做太多额外的工作来解释这一点,但是现在假设有两个路径图被第三个路径图(如数字8)包围:排序后,我们只得到一个孔作为8的一部分。我们也可以解释一下。最后一个问题:假设A包含B,C包含D,但它们按{A,C,B,D}的顺序放入列表中:一些排序算法(如BubbleSort)将按此顺序保留它们,因为没有形状包含它的邻居。这里的列表太混乱了

那么对于我们的树,根节点是什么?根节点将包含所有内容。如果要创建这样一个对象,可以将所有PathGeometrics并用
.Bounds
。也许会有一些奇怪的情况,但这并不重要

我们的树会是什么样子?我将使用您示例中的数字。单击以查看树

我们怎样做这棵树?我认为这个伪代码比我试图描述它更容易理解:

TreeNode.AddNode(PathGeometry geomToAdd)
{
    bool containedByChild = false
    foreach (TreeNode current in this.Children)
    {
        if (current.FillContains(geomToAdd)
        {
            containedByChild = true
            current.AddNode(geomToAdd)
        }
    }
    if (!containedByChild)
        this.Children.Add(geomToAdd)
}
与二叉树不同,我们有一个子元素列表,而不是固定数量的子元素。树中的叶子是子节点列表为空的任何节点。因为根节点应该包含所有内容,所以可以在根节点上调用此方法,而无需为根节点定义PathGeometry

如何将树转化为路径几何体?从root的子级开始。这些是加法路径图形,它们的子对象是减法路径图形。使用
.Combine()
GeometryCombineMode.Exclude
,可以从root的子代中减去root的子代。然后,从根目录中删除所有子目录,并将根目录的曾孙目录转换为新的子目录,然后重复


希望这是清楚的。如果不是,请告诉我如何改进答案。

路径图是否一定不相交?因为如果它们相交,那么事情就会变得更复杂,它们永远不会相交。在应用此操作之前,我正在分析所有几何图形。如果存在交点,将合并相交的几何图形(通过Geometry.Combine(…)和PathGeometry.GetOutlinedPath(…)。GetOutlinedPath函数应防止图形相交。