Reputation:
How do I draw an ellipse with lines of the same length coming out of it?
It's easy to do with a circle, I can just write something like
for (u = 0 ; u < 2*pi ; u += 0.001*pi) {
drawdot (cos(u), sin(u)) ;
drawline (cos(u), sin(u), 2*cos(u), 2*sin(u) ;
}
But if I did that for an ellipse, like below, the lines are different lengths.
for (u = 0 ; u < 2*pi ; u += 0.001*pi) {
drawdot (2*cos(u), sin(u)) ;
drawline (2*cos(u), sin(u), 4*cos(u), 2*sin(u) ;
}
How do I figure out how to make them the same length?
Upvotes: 0
Views: 877
Reputation: 2696
There are a few ways of thinking about this.
You can think of an ellipse as a circle that's been stretched in some direction. In this case, you've taken the circle x^2 + y^2 = 1
and applied the transformation to all points on that curve:
x' = 2x
y' = y
You can think of this as multiplying by the matrix:
[ 2 0 ]
[ 0 1 ]
To transform normals, you need to apply the inverse transpose of this matrix (i.e. the inverse of the transpose, or transpose of the inverse; it's the same thing):
[ 1/2 0 ]
[ 0 1 ]
(This, by the way, is known as the dual of the previous transformation. This is a very important operation in modern geometry.)
A normal to the circle at the point (x,y) goes in the direction (x,y). So a normal to the ellipse at the point (2x,y) goes in the direction (0.5*x,y). This suggests:
for (u = 0 ; u < 2*pi ; u += 0.001*pi) {
x = cos(u); y = sin(u);
drawdot (2*x, y) ;
drawline (2*x, y, 2*x + 0.5*x, y+y);
}
Or if you need a unit normal:
for (u = 0 ; u < 2*pi ; u += 0.001*pi) {
x = cos(u); y = sin(u);
drawdot (2*x, y) ;
dx = 0.5*x;
dy = y;
invm = 1 / sqrt(dx*dx + dy*dy);
drawline (2*x, y, 2*x + dx * invm, y + dy * invm);
}
Another way to think about it is in terms of an implicit contour. If you define the curve by a function:
f(x,y) = 0
then the normal vector points in the direction:
(df/dx, df/dy)
where the derivatives are partial derivatives. In your case:
f(x,y) = (x/2)^2 + y^2 = 0
df/dx = x/2
df/dy = y
which, you will note, is the same as the dual transformation.
Upvotes: 2