Equation to find the Principal Unit Normal of a Bezier curve at $t$ ($0\leq t\leq1$)

bezier-curvedifferential-geometrylinear algebrapartial derivativespline

I have recently been working on Bezier curves and have come across a very interesting snippet of code (don't worry its almost entirely mathematical) relating to finding the principal normal of a Bezier curve. It is the only of its kind I can find and there were no comments left as to how it was derived. The formula boils down to:

$$
(6t^2-6t)P_0 + (3t^2-4t+1)P_1 + (3t^2-2t)P_2 + (-6t^2+6t)P_3
$$

It claims to "Evaluate the normal for value $t$ between points $P_0$ and $P_3$".

My question is: how does this work, if it even does, and how was it derived so I can do the same for a Hermite curve as well. The go to answer for finding the normal would be to just use the second derivative crossed with the tangent and normalised, I have yet to see any other instance where a separate set of polynomials were used to calculate normals, but that is exactly what I need in order to have a generalised function for my program as it will not compute the vectors directly, only the polynomials at some value of $t$ to be used by a user, so I cannot use cross products, or any operations really, directly on the points $P_0,\ldots,P_3$.

If it helps any, I will include the functions I have to compute a point and the derivative in the same style as above, I know that the derivative is not usually represented as 4 distinct polynomials to multiply by, so I did some basic rearranging and have tested to confirm it works properly.

$$
P(t) = (-t^3 + 3t^2 – 3t + 1)P_0 + (3t^3 – 6t^2 + 3t)P_1 + (-3t^3 + 3t^2)P_2 + (t^3)P_3
$$

$$
P'(t) = (-3t^2 + 6t – 3)P_0 + (9t^2 – 12t + 3)P_1 + (-9t^2 + 6t)P_2 + (3t^2)P_3
$$

If you would like to see a more programming oriented version of this question, I originally posted this question on the primary stack overflow site here as I didn't know this site existed. I am making this post because I dont see that question getting much traction on the main site.

To quote myself:

Any help would be appreciated, I have been going though countless
scientific papers and code examples for so long that the word Bezier
gives me ptsd-esque flashbacks at this point.

Best Answer

The code you found is just plain wrong.

Try it on a simple example, say $P_0 = (0,0)$, $P_1 = (1,0)$, $P_2 = (1,1)$, $P_3 = (0,1)$.

It’s obvious that the curve normal at $t=0$ is in the direction $(0,1)$, but that’s not what your code returns.

The right way to calculate the (principal) normal of any curve is as follows:

  1. Calculate the vector $B$ that is the cross product of the first and second derivative vectors. This gives you the direction of the curve’s binormal vector.
  2. Calculate the cross product of $B$ and the first derivative vector. This gives you a vector in the direction of the curve’s principal normal.
  3. If you want a unit normal, then unitize the result from step 2 by dividing it by it’s norm.

Of course, this won’t work if the first and second derivative vectors are linearly dependent. This will happen if they are parallel or one of them is zero. You’ll need special-case code to handle this situation.

At any given point on a curve, there are an infinite number of vectors that are normal to the curve. The procedure outlined above gives you the principal normal (i.e. a normal that lies in the curve’s osculating plane).

See sections 2.2 and 2.3 in this book.

If you want the curve normal at its start point, where $t=0$, you can take some shortcuts. Let $U = P_1 - P_0$, and $V = P_2 - P_1$. Then the binormal vector $B$ is in the direction of the cross product $U \times V$, and the normal is therefore in the direction of $(U \times V) \times V$.