Getting the intersection points of two [path] geometries in WPF

While working on an app that utilises geometries in WPF, I needed a way to get the intersection points of the lines of two arbitrary geometries. A google search didn’t yield any useful hints except a post suggesting to use mathematics. That would be ideal for very simple geometries like lines, but with complex geometries, it becomes tiresome real quick. The framework doesn’t seem to have any built in functions that calculate that, so it’s time for some hack and slash.

After a few days of thinking, I came up with a simple, yet effective (but not the most efficient solution). For those who just want the intersection between two geometries, there is the CombinedGeometry geometry class which takes input in the form of two geometries. Setting the GeometryCombineMode to Intersect gives a geometry which is the intersection of the two. At the otherside of the WPF realm, we have Geometry.GetWidenedPathGeometry(). This method basically converts/strokes path lines to an approximate geometry. Combining these two concepts, we can produce an intersection from two widened path geometries (the two paths which we want the intersection of).

[csharp]
public static Point[] GetIntersectionPoints(Geometry g1, Geometry g2)
{
Geometry og1 = g1.GetWidenedPathGeometry(new Pen(Brushes.Black, 1.0));
Geometry og2 = g2.GetWidenedPathGeometry(new Pen(Brushes.Black, 1.0));

CombinedGeometry cg = new CombinedGeometry(GeometryCombineMode.Intersect, og1, og2);

PathGeometry pg = cg.GetFlattenedPathGeometry();
Point[] result = new Point[pg.Figures.Count];
for (int i = 0; i < pg.Figures.Count; i++)
{
Rect fig = new PathGeometry(new PathFigure[] { pg.Figures[i] }).Bounds;
result[i] = new Point(fig.Left + fig.Width / 2.0, fig.Top + fig.Height / 2.0);
}
return result;
}
[/csharp]

The function will return an array of zero or more points of intersection. To test it

[csharp]
sg1 = StreamGeometry.Parse("M0,0 L100,100");
sg2 = StreamGeometry.Parse("M0,100 L100,0");
Point[] pts = GetIntersectionPoints(sg1, sg2);
// pts[0] is {50,50}
[/csharp]

Hope this helps someone.

6 thoughts on “Getting the intersection points of two [path] geometries in WPF

  1. Christof

    Great idea.

    what is wrong with just returning the StartPoint of the figures?

    return pg.Figures.Select(f => f.StartPoint);

    In all my tests it seems to work and doesn’t involve the extra loop at the end.

  2. Loune Post author

    It’s certain possible to just use f.StartPoint. The loop simply gets the center point of the figure which adds precision to the result. In geometry figures that are big, it won’t matter, but in small figures with decimal point precision, it’ll make a difference.

  3. Jegan

    Is there any efficient way to do the same, because there is performance issue if i use this code very frequently.

  4. Yury

    Thanks a lot for this blog entry. It works perfect and the performance is more than enough for my requirements. A real life saver, what seemed like a difficult math puzzle was implemented in under 5 minutes. :D

  5. Pingback: Intersection of two WPF geometries « Mas-Tool's Favorites

  6. JAY PATEL

    I have two “PathSegment”s which are child of two different “PathFigure”s so how can i find Intersection of those two pathSegments?

Leave a Reply

Your email address will not be published. Required fields are marked *