## Homework 7, due Tuesday, Nov 23.

Splines:

In class I talked about parametric cubic splines, and briefly mentioned parametric bicubic surface patches. This assignment has two parts:

1. Implement an interactive Java applet that shows its user some cool picture made out of spline curves, and allows the user to drag around control points to modify that picture.

2. Implement an interactive Java applet that allows the user to manipulate bicubic spline patches. You can use Bezier, BSpline, Catmull-Rom or Hermite patches, or the option for more than one of these if you're feeling ambitious. At the very least, allow the user to edit the geometry of a single bicubic patch. Then when you get that working, try to allow the user to edit the geometry of multiple bicubic patches that fit smoothly together.

For this assignment you'll want to go back to using the `java.awt.graphics` support class that you used earlier in the semester, since you'll mostly be drawing lines and circles - you will be making curves by drawing lots of little successive lines end to end.

For both parts of this assignment, feel free to use the Cubic.java class that provides cubic spline support fo the interactive cubic curve applet that I showed in class. This week I really want you to concentrate on a nice interactive tool for curve and surface editing.

Your first program should behave as follows:

• Create a picture of something cool out of some sort of cubic curves, such as Bezier curves. You might want to create an interesting cartoon character, or some sort of fancy letter shape, or perhaps something political or a hopeful Thankgiving theme. Remember that you can also use different colors to make things more interesting. If you're feeling a little ambitious, you can try to create filled-in shapes by using the `fillPolygon` method, rather than just draw curves via the `drawLine` method.

• If you choose Bezier curves, remember that every third control point in curve specified with Bezier splines (ie: control points P0, P3, P6, etc), is an interpolating control point that acts as the first and last control point for an individual Bezier spline.

• When the user drags on a control point (ie: does a mouseDown event very close to that control point, followed by a sequence of mouseDrag events), the applet should move that control point, so that it follows the cursor position.

• You might want to explicitly have an "edit" mode, in which you show a faint line between successive control points (perhaps in a gray or pink or light blue color), and mark the interpolating control points P0, P3, P6, etc, with large dots (using the `fillOval` method) to show that those control points are the ones which mark the beginning and end of the individual Bezier cubic spline curves.

An important thing to keep in mind is that if you want two successive Bezier curves that share some key point P3n to join together without a sharp bend between them, then you must make sure that the slope from P3n to the next key point P3n+1 is equal to the slope from the previous key point P3n-1 to P3n. In order to constrain the key points so that successive spline segments maintain the same slope at their common point when the user drags control points around, you should do something like the following:

• When the user moves some interpolating key point P3n, you should move the two key points before and after it ( P3n-1 and P3n+1 by the same amount.

• When the user moves one of the non-interpolating key points, then you should move the key point on the other side of the nearest interpolating key point so that the three successive key points P3n-1, P3n, P3n+1 remain co-linear.

• To draw the actual curve, plot the individual Bezier curves defined by key points (P0,P1,P2,P3), (P3,P4,P5,P6), etc., as described below.

As we covered in class, the way you define a cubic curve is to treat the x geometry and the y geometry independently, creating a different parametric cubic curve for each coordinate dimension.

For every type of spline there is a unique matrix that transforms the four geometry values in each dimension to the cubic polynomial at3+bt2+ct+d. For example, you can construct Bezier splines by:

```
Cubic xSpline = new Cubic Spline(Cubic.BEZIER, GX);
Cubic ySpline = new Cubic Spline(Cubic.BEZIER, GY);
```

where `double GX[], GY[]` are each arrays containing the four geometry values for their respective coordinate.

This constructor uses the matrix to transform the four geometry values into (a,b,c,d), which will let you evaluate the cubic polynomials:

X(t) = axt3 + bxt2 + cxt + dx
Y(t) = ayt3 + byt2 + cyt + dy

where each evaluation is implemented by `xSpline.eval(t)` and `ySpline.eval(t)`.

Once you know the cubic polynomials that define X(t) and Y(t) for any individual parametric cubic curve, the simplest way to draw the curve is to loop through values of t, stepping from 0.0 to 1.0, and draw short lines between successive values. For example, if you have already defined methods `double X(double t)` and `double Y(double t)`, then you can use code structured something like:

```   for (double t = 0 ; t <= 1 ; t += ε)
g.drawLine((int)X(t), (int)Y(t), (int)X(t+ε), (int)Y(t+ε));
```

Similarly, you can define the coordinates at (u,v) on a bicubic patch by X(u,v),Y(u,v),Z(u,v) by using the bicubic constructors in the Cubic class. For example, you can construct Bezier surface patches by:

```
Cubic xSpline = new Cubic Spline(Cubic.BEZIER, GX);
Cubic ySpline = new Cubic Spline(Cubic.BEZIER, GY);
Cubic zSpline = new Cubic Spline(Cubic.BEZIER, GZ);
```

where `double GX[][],GY[][],GZ[][]` are each arrays containing the sixteen geometry values for their respective coordinate.

You can then fill up a geometric mesh (sort of like you did when you made sphere meshes) by:

```   for (int j = 0 ; j < nRows ; j++)
for (int i = 0 ; i < nCols ; i++) {
double u = (double)i / nCols;
double v = (double)j / nRows;
defineVertex(i, j, X(u,v), Y(u,v), Z(u,v));
}
```

where X(u,v), Y(u,v) and Z(u,v) are implemented by `xSpline.eval(u,v)`, `ySpline.eval(u,v)` and `zSpline.eval(u,v)`, respectively.