# Polygons

One of the simplest things you can draw is a polygon. There are many ways to draw them in Nell. To draw an equilateral triangle with sides of length 1 you could use the program (poly00.nll).

#### Program: (poly00.nll)

```START : L(1) T(2*pi/3) L(1) T(2*pi/3) L(1) T(2*pi/3);
```

#### Command line

`nell poly00.nll START 6 | nellsvg 1 1 in 0.02 1 > poly00.svg`

The exterior angles of an equilateral triangle are all equal to 120 degrees = 2*pi/3 radians, hence the `T(2*pi/3)` commands. The last `T(2*pi/3)` command is strictly not necessary. It just returns the direction to where it was at the beginning.

The program (poly00.nll) will produce an svg where each line is a separate path. To group all the lines into a single path, we simply put angle brackets around the command string as shown in program (poly00a.nll)

#### Program: (poly00a.nll)

```START : <L(1) T(2*pi/3) L(1) T(2*pi/3) L(1) T(2*pi/3)>;
```

#### Command line

`nell poly00a.nll START 6 | nellsvg 1 1 in 0.02 1 > poly00a.svg`

This produces an svg where the triangle is a single path, but the path is still open, i.e. the first point is not connected to the last point. A triangle that is a single closed path is produced by program (poly01.nll)

#### Program: (poly01.nll)

```START : <L(1) T(2*pi/3) L(1) T(2*pi/3) Z()>;
```

#### Command line

`nell poly01.nll START 6 | nellsvg 1 1 in 0.02 1 > poly01.svg`

Note that the last L(1) command has been left out since it is implicit in the Z() command which closes the path and sets the current position and direction to what it was at the start of the path.

You can use this same technique for drawing regular polygons with any number of sides, but instead of writing out the L commands for each side explicitly, you can use a substitution command. The program (poly02.nll) shows how to do this to draw a pentagon.

#### Program: (poly02.nll)

```SIDE : L(1) T(2*pi/5);
START : M(0.5) <S(SIDE,4) Z()>;
```

#### Command line

`nell poly02.nll START 6 | nellsvg 2 2 in 0.02 1 > poly02.svg`

The command string labeled `SIDE` draws one side of the pentagon, and we use it four times inside the path to draw four sides of the polygon with the final `Z` command completing the last side. The initial `M(0.5)` command starts the drawing at the point (0.5,0) so that the entire pentagon is in the positive first quadrant.

With a substitution command and a variable definition we can easily generalize this to a program that will draw a polygon with `n` sides. Program (poly03.nll) shows how it's done.

#### Program: (poly03.nll)

```n = 6;
SIDE : L(1) T(2*pi/n);
START : M(0.5) <S(SIDE,n-1) Z()>
```

#### Command line

`nell poly03.nll START 6 | nellsvg 2 2 in 0.02 1 > poly03.svg`

In (poly03.nll) we've defined the variable `n` which is set equal to 6 at the beginning of the program. If you run the program like this it will produce a hexagon. Set `n = 8;` and it will produce an octagon and so on.

So much for drawing single regular polygons. Now let's see how easy it is to create drawings with multiple polygons. You can easily make a series of nested regular polygons using a double set of substitutions. Program (poly04.nll) shows how it's done.

#### Program: (poly04.nll)

```n=3;
SIDE : L(1) T(2*pi/n);
POLY : <S(SIDE,n-1) Z()> A(n,n+1);
START : M(1) S(POLY,6);
```

#### Command line

`nell poly04.nll START 6 | nellsvg 3 3 in 0.02 1 > poly04.svg`

In (poly04.nll) we've used the `A` command that assigns a new value to a variable, which in this case is the number of sides in the next polygon to draw. The `POLY` command string is substituted 6 times with the value of `n` incremented each time, starting with the value 3. The result is that a triangle, square, pentagon, hexagon, heptagon, and octagon are drawn, all starting at the same point and sharing a common side. The `M(1)` command sets the starting point for all polygons to (1,0) so they are horizontally centered on a 3 by 3 canvas.

Program (poly05.nll) shows how to arrange five pentagons so that they form a pentagon.

#### Program: (poly05.nll)

```SIDE : L(1) T(-2*pi/5);
POLY : <S(SIDE,4) Z()> M(1) T(2*pi/5);
START : P(2,2) S(POLY,5);
```

#### Command line

`nell poly05.nll START 6 | nellsvg 5 5 in 0.02 1 > poly05.svg`

Here we've used the `P` command to position the starting point at (2,2). This centers the drawing on a 5 by 5 canvas. The `POLY` command string draws a pentagon, moves one unit in the current direction and changes direction by `2*pi/5` so that the next pentagon can be drawn.

The program (poly06.nll) draws a pentagram inside a pentagon.

#### Program (poly06.nll)

```d = (1+sqrt(5))/2;
PENTAGON : <L(1) T(2*pi/5) L(1) T(2*pi/5) L(1) T(2*pi/5) L(1) T(2*pi/5) Z()>;
PENTAGRAM : T(pi/5) <L(d) T(4*pi/5) L(d) T(4*pi/5) L(d) T(4*pi/5) L(d) T(4*pi/5) Z()>;
START : M(0.5) S(PENTAGON,1) S(PENTAGRAM,1);
```

#### Command line

`nell poly06.nll START 6 | nellsvg 2 2 in 0.02 1 > poly06.svg`

The program (poly07.nll) draws concentric triangles starting with the outer triangle and going in.

#### Program: (poly07.nll)

```n = 6;
l = 2;
dl = l/n;
dr = dl/sqrt(3);
a = 2*pi/3;
TRI : <L(l) T(a) L(l) T(a) Z()> T(pi/6) M(dr) T(-pi/6) A(l,l-dl);
START : S(TRI,n);
```

#### Command line

`nell poly07.nll START 6 | nellsvg 2 2 in 0.02 1 > poly07.svg`

The variable `n` defines the number of triangles to draw. The variable `l` is the length of a side of the outer triangle. The variable `dl` is the amount by which the length of the triangle side changes as you go in. The variable `dr` is the length by which you move in to draw the next triangle. As an exercise see if you can modify the program so the inner triangle is drawn first and the outer last.

You can generalize (poly07.nll) to draw concentric polygons with any number of sides. The program (conpoly.nll) shows how to do it.

#### Program: (conpoly.nll)

```ns=6;  number of sides
n=12;  number of polygons
l=2;  length of a side
dl=l/n;
dr=dl/(2*sin(pi/ns));
a=2*pi/ns;
b=pi*(ns-2)/(2*ns);
SIDE : L(l) T(a);
POLY : <S(SIDE,ns-1) Z()> T(b) M(dr) T(-b) A(l,l-dl);
START : M(1) S(POLY,n);
```

#### Command line

`nell conpoly.nll START 10 | nellsvg 4 4 in 0.02 1 > conpoly.svg`

The program defines the variable `ns` that specifies the number of sides for the polygons and the variable `b` which is the angle to turn to move to the beginning of the next inner polygon.

A variation on the concentric polygons is to rotate each of the inner polygons by half the exterior angle. The program (rconpoly.nll) shows how to do it.

#### Program: (rconpoly.nll)

```ns=8;  number of sides
n=28;  number of polygons
l=2;  length of a side
a=2*pi/ns;
rl = cos(a/2);
SIDE : L(l) T(a);
POLY : <S(SIDE,ns-1) Z()> M(l/2) T(a/2) A(l,l*rl);
START : M(sqrt(2)) S(POLY,n);
```

#### Command line

`nell rconpoly.nll START 10 | nellsvg 4.83 4.83 in 0.02 1 > rconpoly.svg`

We can also easily tile polygons. The program (tritile.nll) will create a tiling using triangles.

#### Program: (tritile.nll)

```n = 8;
l = 0.5;
r = 1.0;
d = r*l;
a = 2*pi/3;
T1 : <L(l) T(a) L(l) T(a) Z()> M(d);
T2 : [S(T1,n)] T(a/2) M(d) T(-a/2) [S(T1,n-1)];
T3 : [S(T2,1)] T(pi/2) M(d*sqrt(3)) T(-pi/2);
START : S(T3,n/2);
```

#### Command line

`nell tritile.nll START 10 | nellsvg 4 4 in 0.02 1 > tritile.svg`

The variable `n` is the number of triangles per row, `l` is the length of a triangle side and `r` determines the tile spacing where `r=1` gives an exact fit, `r<1` gives an overlap, and `r>1` adds space between the triangles. For `r=1.25` we get this:

The program (hextile.nll) will create a tiling using hexagons.

#### Program: (hextile.nll)

```a = pi/3;
s = 0.5;
r = 1.0;
d = r*s*sqrt(3);
n = 4;
T1 : L(s) T(a);
T2 : <S(T1,5) Z()>;
T3 : S(T2,1) T(a/2) M(d) T(-a/2) S(T2,1) T(-a/2) M(d) T(a/2);
T4 : [S(T3,n)] T(pi/2) M(d) T(-pi/2);
START : M(0.25) S(T4,n);
```

#### Command line

`nell hextile.nll START 10 | nellsvg 6.25 4.0 in 0.02 1 > hextile.svg`

Again the variable `r` determines the spacing. For `r=1` there is no space between the hexagons. For `r=0.5` the hexagons overlap as in the following figure.