Search code examples
pythonmathspline

Catmull-Rom splines in python


Is there a library or function in python to compute Catmull-Rom spline from three points ?

What I need in the end are the x,y coordinates of points along the spline, provided that they are always equidistant of a given amount t along the spline (say, the spline curve is 3 units long and I want the x,y coordinates at spline length 0, 1, 2 and 3)

Nothing really exciting. I am writing it by myself, but if you find something nice, It would be great for testing (or to save time)


Solution

  • 3 points ? Catmull-Rom is defined for 4 points, say p_1 p0 p1 p2; a cubic curve goes from p0 to p1, and outer points p_1 and p2 determine the slopes at p0 and p1. To draw a curve through some points in an array P, do something like this:

    for j in range( 1, len(P)-2 ):  # skip the ends
        for t in range( 10 ):  # t: 0 .1 .2 .. .9
            p = spline_4p( t/10, P[j-1], P[j], P[j+1], P[j+2] )
            # draw p
    
    def spline_4p( t, p_1, p0, p1, p2 ):
        """ Catmull-Rom
            (Ps can be numpy vectors or arrays too: colors, curves ...)
        """
            # wikipedia Catmull-Rom -> Cubic_Hermite_spline
            # 0 -> p0,  1 -> p1,  1/2 -> (- p_1 + 9 p0 + 9 p1 - p2) / 16
        # assert 0 <= t <= 1
        return (
              t*((2-t)*t - 1)   * p_1
            + (t*t*(3*t - 5) + 2) * p0
            + t*((4 - 3*t)*t + 1) * p1
            + (t-1)*t*t         * p2 ) / 2
    

    One can use piecewise quadratic curves through 3 points -- see Dodgson, Quadratic Interpolation for Image Resampling. What do you really want to do ?