Search code examples
c#image-processingcubic-spline

Extracting points coordinates(x,y) from a curve c#


i have a curve that i draw on a picturebox in c# using the method graphics.drawcurve(pen, points, tension)

is there anyway that i can extract all points (x,y coordinates) been covered by the curve ? and save them into an array or list or any thing would be great, so i can use them in a different things.

My code:

void Curved()
{
    Graphics gg = pictureBox1.CreateGraphics();
    Pen pp = new Pen(Color.Green, 1);
    int i,j;
    Point[] pointss = new Point[counter];

    for (i = 0; i < counter; i++)
    {
        pointss[i].X = Convert.ToInt32(arrayx[i]);
        pointss[i].Y = Convert.ToInt32(arrayy[i]);
    }
    gg.DrawCurve(pp, pointss, 1.0F);
}

Many thanks in advance.


Solution

  • If you really want a list of pixel co-ordinates, you can still let GDI+ do the heavy lifting:

    using System.Collections.Generic;
    using System.Diagnostics;
    using System.Drawing;
    using System.Drawing.Drawing2D;
    
    namespace so_pointsfromcurve
    {
        class Program
        {
            static void Main(string[] args)
            {
                /* some test data */
                var pointss = new Point[]
                {
                    new Point(5,20),
                    new Point(17,63),
                    new Point(2,9)
                };
                /* instead of to the picture box, draw to a path */
                using (var path = new GraphicsPath())
                {
                    path.AddCurve(pointss, 1.0F);
                    /* use a unit matrix to get points per pixel */
                    using (var mx = new Matrix(1, 0, 0, 1, 0, 0))
                    {                    
                        path.Flatten(mx, 0.1f);
                    }
                    /* store points in a list */
                    var list_of_points = new List<PointF>(path.PathPoints);
                    /* show them */
                    int i = 0;
                    foreach(var point in list_of_points)
                    {
                        Debug.WriteLine($"Point #{ ++i }: X={ point.X }, Y={point.Y}");
                    }
                }
    
            }
        }
    }
    

    This approach draws the spline to a path, then uses the built-in capability of flattening that path to a sufficiently dense set of line segments (in a way most vector drawing programs do, too) and then extracts the path points from the line mesh into a list of PointFs.

    The artefacts of GDI+ device rendering (smoothing, anti-aliasing) are lost in this process.