# Chapter 1: Introduction > "Skill to do comesof doing." Ralph Waldo Emerson > "Chance favors the prepared mind." Louis Pasteur ### Who I hope you are You might be interested in the studio arts--painting, drawing, sculpture, photography--or in architecture. You may have had experience in graphic, commercial, or industrial design. Then again, you might be a liberal arts type with a background in language, literature, music, or science. Or perhaps you are a professional type educated in the field of business, law, medicine, or theology. You could be a student or a teacher or neither or both. You may have spent long hours in art studios and possess an exceptionally rich, visual vocabulary. Then again, your graphic abilities, both verbal and physical, may be very much on the thin side. Instead, your vocabulary might be skewed toward logic and mathematical terms because your background is in the sciences, philosophy, law, or mathematics. Perhaps you are that much sought after, well-rounded person whose vocabulary is rich without being specialized. You may not be able to describe every phase that Picasso went through, but you enjoy looking at art, and you can differentiate a Picasso from, say, a Pissarro when you see them side by side. You probably have a favorite artist or a favorite period, and you have paintings or reproductions of them in your own home. While you may not be able to sketch the Acropolis using 3--point perspective, you do have some idea of what perspective means. You would be intrigued by the suggestion that, in fact, there are dozens of different ways to illustrate objects in space. At some time in your past, you must have taken a course in geometry. (Everybody has taken a course in geometry. It is one of the few bits of liberal education that we still share.) What about trigonometry? You may have forgotten everything, but you aren't brought to the edge of coronary arrest by hearing the words _geometry_ and _trigonometry_. Finally, and most important, whatever your curriculum vitae says, and whatever type of intellectual or visual baggage you carry, _I hope that you are excited by looking at things and by thinking about how things look._ This book will show you how to increase this kind of excitement by encouraging you to build a special, visual variety of computer models. If you are stimulated by this idea, then you are exactly who I hope you are. ### Your computer baggage This chapter gives a very quick summary of basic Ludus. It is brief, not just because I hope that you already know a little Ludus but because I expect that you are willing to use the reference that comes with the Ludus web interpreter. In other words, I expect that you are willing to do some learning about Ludus mechanics on your own. If you have never met Ludus before, probably you have been introduced to some other computer language and most likely this other language was BASIC. (I am saddened to think of you learning BASIC before Ludus, and this book will give you the chance to right that terrible wrong.) > Reader, we do not actually expect BASIC to have been your first language, although we share Clayson's distate for it. Likely your first language was Javascript, or Python, or Processing, or maybe even Scratch. The distance from these to Ludus is not unlike the distance from BASIC to Logo was. If you do know something about one computer language, you should be able to plunge happily into the manual of a second language--Ludus. I will give you some directional help, though, by suggesting what questions you need answered in your manual. Then it will be up to you to learn the specifics. I assume, too, that you have played around with personal computers and know how they "feel." You may like or dislike these machines, but your feelings are based on personal experience. You are familiar with disks, disk drives, keyboards, and program editors. > In fact, we expect you may well not be familiar with disk drives, but it's definitely good to have some familiarity with a keyboard. ### No baggage If you have had no experience with personal computers, and have never tried to learn a computer language--on your own or in a course--you may find this book rough going. If, on the other hand, you have access to a teacher, tutor, or friend who is willing to give you help when you ask for it--and if you are patient, curious, and tenacious--I think you should stick around. ### Programming as craft Learning to program in Ludus is very much like learning a craft. You can read about "doing Ludus" as you can read about making furniture, and you can talk to others about doing it as well. But in order to develop the individual talents and skills do old needed for yourself. For the newcomer to a craft, a master artisan can certainly be of help. The old timer can suggest small, beginning projects that are reasonably taxing but not overly intimidating. And by offering encouragement, he can keep the novice's spirits high. This chapter is designed to reinitiate you into the excitement of Ludus craft; all the exercises within the chapter have been fashioned by an experienced craftsman. These initial projects should be copied. All artisans begin learning their craft by copying what others have done. This is not to deny their creativity but rather to allow for a strengthening of the basic skills that support individual creativity. Good craftsmanship, of course, requires both skill and creative flair. For my purposes, skills are as much frames of mind as forms of physical dexterity. For example, in this chapter I will stress the usefulness of three such skills: first, an ability to break down big problems into smaller problems; second, a willingness to imagine yourself as "walking" shapes into existence; and third, a propensity to tinker with your Ludus machinery. Very soon (starting with the exercises at the end of this chapter, in fact) you will be asked to apply these skills to support your own kind of invention. Craft is about building things by hand, and that is what you will be doing with Ludus. ### Copying and tinkering Copying computer programs is so widespread that I had better give you my opinion about the usefulness of it all. In the previous paragraph I said that copying was a good thing at the start of one's apprenticeship. As you go through this chapter, I hope you will want to try out my functions. That's OK. But if you simply type my functions into your computer, you will only reproduce what I have done. And that will bore us both. The book shows what I have done; it doesn't show what you can do. My functions offer you a starting place, so that you don't have to build from zero. But it is up to you to go beyond that start. So please do copy the ideas of any function that strike your fancy. But, once you have made those ideas work on the screen, play rough with them. Give the copied function funny and outlandish arguments. (Very big or very small numbers could be outlandish, but what is a funny argument?) What happens then? Does your copied function still work? Can you explain how? Go on to make a few changes inside the body of the function; change some of the commands just a little. Can you guess what might happen before you experiment on these changes? Get into the habit of tinkering, just a little. Whenever you write, or copy, a nice function, make a few changes to it so that it does something else. ### Equipment Your most important piece of equipment is a notebook. It is far more important than the computer you work on and the documentation you consult. Select a notebook with large, unlined, and bound-in pages. I want you to keep track of your work in this notebook. That means everything: the little sketches, word portraits, diagrams, function listings, the printed images. Stick in any magazine and newspaper illustrations that strike your fancy, whenever you find them; don't worry aobut organization. You will be mixing the good with the less than good, the things that worked well with those that never will. I suggest that a large format notebook is best. That means plenty of room for a lot of stuff. Small notebooks encourage crabbed handwriting and get messy; you will need a lot of space. Also, unlined paper is better. Since there is no need to write carefully, lines will get in the way. If you need graph paper for a careful diagram, glue a piece in. And, finally, the bound--in pages will not let you reorganize the book. The notebook may organize you. Glue. Rubber cement is the Queen of Glues and the world's best notebook adhesive. Get a lot of it. Be careful using this glue, though; it is very flammable. Don't smoke and glue at the same time. > Don't smoke at all. > But seriously, even though you might imagine that we're fully digital, nearly four decades later, we encourage you, still, to use pen and paper liberally. Rubber cement may be less interesting, and you're probably not reading magazines. But we take tools and media and affordances seriously, and pen and paper are what you want, not some shiny new digital toy. > Oh, and you _will_ need Ludus: [web.ludus.dev](https://web.ludus.dev). ### Caveat emptor This is a little late for a warning, but here it is anyway: _This is not a book about Ludus._ You will end up knowing a lot about Ludus, and that is no bad thing. But the goal of the book is to get you to build visual models, and Ludus is only a means to that end. God knows, we could have used Python. But it just so happens that Ludus is easier to learn and easier to use than most of the other languages that we could have selected. Ludus notation is neat and tidy; it looks nice on the page and that encourages visual thinking. But most important, because Ludus is so easy to play around with, it won't get in the way. > In fact, while we're sure Logo had some of these advantages over its competition (Clayson used Pascal, not Python, as his strawman here), we have different ideas about what's interesting about Ludus than what Clayson notes here. We think Ludus, like Logo, is better for learning _how to think well with computers_, and that it teaches a different set of things than you might learn in a typical introductory programming situation, whether that be computer-scientific, artistic or creative, or digital-humanistic. ### Turtles are us We will concentrate on the graphic parts of Ludus. And that means "turtle graphics," which Ludus borrows from Logo. The intent of Logo's turtle metaphor was to inspire young children to explore shapes. The turtle is a tiny triangle of light that is moved about the screen via Ludus commands. As the turtle moves, it leaves a trace of light. Children are encouraged to imagine themselves in the turtle's place and to draw a shape by walking through it, as the turtle would walk through it. Children have the necessary body knowledge to walk a circle, even though they cannot express their circle drawing rules before walking them. Walking the turtle around an invisible circle translates the body's knowledge into word commands: "I'm walking him forward a little bit, now I'll turn him a little, I'm walking him forward a little bit, now I'll turn him a little... I'll keep doing this until until he's finished. Yes, that's it; I'm back where I started." Once said, the words are available to be transformed into Ludus commands. Because adult bodies may be more spatially intuitive than children's, your turtle visualizations can be far more effective than a child's. There is a problem with adults, though; they aren't used to playing imagination games as adults and must be coaxed into it. Children are happy to play silly games; adults may be embarrassed to try. I will be asking you, after all, to imagine yourself as an electronic turtle. And what would that feel like, I mean physically? Use your turtle body and walk around a bit. Don't reject visualization and muscular thinking before you try it. What was good enough for Uncle Albert should be good enough for you. Listen to what he said: "The physical entities which seem to serve as elements in thought are certain signs and more or less clear images which can be 'voluntarily' reproduced and combined... this combinatory play seems to be the essential feature of productive thought. The above elements are, in my case, of the visual and some of the muscular type."--Albert Einstein ### Turtle space Turtles live on your computer screen. The turtle is moved forward, backward, turned left or right in relation to where it is now. Review the [Ludus documentation for turtle commands](https://alea.ludus.dev/twc/ludus/src/branch/main/prelude.md#turtle-graphics), especially: `forward!`, `back!`, `penup!`, `pendown!`, `right!`, `left!`. In the cartesian system, the destination is the important thing; in the turtle reference system, it's the trip. ### Making shapes Let's draw a simple shape using turtle reference commands. Suppose you would like the turtle to draw a square box located at the center of the screen (usually the origin of the coordinate system). First, you would think about the commands needed to walk the turtle through the shape. _Use_ the turtle metaphor. 1. "OK turtle? Go forward 50 steps and turn right by a quarter turn. That completes the left side of the box." 2. "Now, go forward another 50 steps and turn right by a quarter turn. That completes the top of the box." 3. "Go forward yet another 50 steps and turn right again by a quarter turn. That completes the right side of the box." 4. "Go forward another 50 units and turn right a quarter turn. That completes the bottom edge of the box." That's it. The turtle has walked around the four sides of a size 50 box, arriving back to where it started. These prose commands would translate into Ludus as: ``` forward! (50) right! (0.25) forward! (50) right! (0.25) forward! (50) right! (0.25) forward! (50) right! (0.25) ``` The third and last step would be to type these commands on the keyboard. And here is what you will see. {{Figure 1: A simple box. Top of p. 10.}} > You might consider copying and pasting. That would certainly be easier! But actually, we encourage you to type out everything by hand. It gives you a kind of muscle memory for the language. Great. This series of commands does indeed draw the square you wanted; but wasn't it tedious to type in all that stuff? The commands `forward! (50)` and `right! (0.25)` were typed four times. Surely there is a shorthand method to repeat this line four times without typing four times. Thus the `repeat` form; it is exactly what we need here. Try it. ``` repeat 4 { forward! (50) right! (0.25) } ``` Notice that this code is a kind of operational definition of what a square is: a square is four sides, four `forward! ()` calls, with each side joined at right angles to the next, the `right! (0.25)` calls. That's tidy, but it's still a bore to type two lines each time you want a size 50 box on the screen. After all, you may want to draw 100 boxes. Wouldn't it be convenient to be able to "tell" Ludus your definition of a square and then to give that definition a name? ### Ludus functions group commands under a single name You can group a series of Ludus commands together under a single name by writing a Ludus function. The name of the function is a shorthand for all commands included in it. Typing the name of the function tells Ludus to automatically execute each line of the function in turn, just as if you had typed them, one after another, on the keyboard. You can "tell" Ludus your definition of a square by creating a function called `box!`. Ludus will "remember" your definition until you either erase it or turn off your computer. Review the defining and editing functions in your Ludus manual. > You will notice that all the function names we have used so far end with an exclamation point. These are part of the name of the function, but they don't mean anything special to Ludus. They do, however, mean something special to Ludus programmers: this function is a command. It makes something happen. Later on in this chapter, we will meet a few different kinds of functions: arithmetic functions and predicates. Stay tuned. ### Shapes defined and drawn by functions Let's get on with writing the necessary function. Here it is: ``` fn box50! () -> { repeat 4 { forward! (50) right! (0.25) } } ``` Ludus will add `box50!` to all its other commands. Each time you type `box50!`, the turtle will draw a square of size 50. The figure will be drawn at the turtle's current position on the screen. Unless you move the turtle to a different starting point, each time you type `box50!`, the square produced will be on top of the previously drawn figure. So move the turtle around to new positions and draw some more boxes. But you can certainly be more imaginative than that. Create an interesting design on the screen using only the `box50!` function and move commands. If you have a color screen, you might want to investigate the effects of changing the screen's background color and the color of the pen. Keep track of what you are doing in your notebook so that you can reconstruct your successful designs. Here is a simple command that wraps boxes around the screen: ``` repeat 25 { pendown! () box50! () penup! () right! (inv (24)) forward! (60) left! (inv (24)) } ``` ### Wrapped boxes Here are two different images produced by that one-liner. How are they different? Is one image more pleasing than the other? Why? {{Figures 2 & 3: Wrapped boxes. Bottom of p. 12.}} ### Generalizing functions What about boxes of different sizes? You could edit the `box50!` function every time you wanted it to draw a different size box. You could also define many `box`-like functions, each to draw a different size box. But that doesn't seem very efficient, does it? After all, Ludus itself doesn't have a different `forward!` command for every possible length of line that you might wish the turtle to draw. There is not a `forward!10` command for drawing lines of length 10 and a `forward!43` command for drawing them 43 units long. Ludus has a single `forward!` command. Whenever `forward!` is used, an argument must be used in conjunction with it: the form is `forward!` argument. A single argument must be typed just after `forward!`. For example, one could type: `forward! (10)` or `forward! (43)`. The value of the argument "tells" `forward!` how to go about its business of drawing straight lines. Isn't this convenient? One command does a variety of things. `forward! (argument)` draws straight lines of _any_ length. If we change the value of the argument, the line length changes accordingly. Let's _generalize_ `box50!` in terms of box size as `forward!` is _general_ in terms of line length. ### Adding an argument to a function Define a new box function that has a size argument. The value of the argument will tell the box function how to go about its business of drawing boxes. Changing the value of the argument will change the size of the box. You can now draw boxes of any size from, say, 1 unit to 5000 units. Use this example as a "pattern" for incorporating an argument into a function. ``` fn box! (edge) -> { repeat 4 { forward! (edge) right! (0.25) } } ``` ### Putting a demonsuation function together I am sure that by this time you have already designed some interesting patterns with various `box!` functions. Some of these patterns you probably liked enough to print and glue into your notebook. Remember to include a few written comments on what you were trying to achieve. Perhaps you would like to show off your designs. You could show your pals the images in your notebook. But seeing an image is not the same as seeing how the image is drawn, the order in which the pieces are visually assembled. How would you go about demonstrating this? You could retype all the Ludus commands needed for your screen collage. What else could you do? Remember that Ludus functions can group a series of commands together under one name. So let's define a new Ludus function that will run all the necessary steps to demonstrate your design. Once defined, you will only have to type the demonstration function's name to have your designs redrawn on the screen. Your demonstration function will have no arguments; it will only do one thing: generate a specific design that you want to show to your friends. If you wish to show off with several designs, you could design specific Ludus functions to reproduce eachdesign. Here is an example of such a demonstration function: ``` & A demonstration function to show off a design & produced from multiple boxes of different sizes. fn demo! () -> { repeat 4 { box! (100) box! (98) box! (96) box! (75) box! (40) box! (35) box! (30) right! (0.25) } } ``` To see the pattern defined by `demo!`, type it: {{Figure 4: Differently sized boxes. Top of p. 15.}} ### Funny feelings Do you have a funny feeling that this isn't enough, that we aren't producing great enough images? Let's think about this for a while. Drawing with Ludus should not be the same as drawing with a pen or pencil. What can be sketched quickly by hand is unbearably tedious to sketch with Ludus. You may have tried sketching with Ludus by moving the turtle as you would move your sketching hand. It doesn't satisfy, and it doesn't work. Ludus is a unique medium for visual expression; don't expect it to be like other media. Visual modeling with Ludus is as different from drawing as clay modeling is different from photography. Our Ludus media is a visual modeling media. We use it best to build models. Why? To encourage us to think about shapes. The drawing is done to encourage thinking. So don't worry too much (now) about the final image. Don't worry if your designs aren't amazingly beautiful; don't be concerned if they aren't "arty." This isn't, after all, a book about computer "art," but it might be useful to think about ART for a minute. Here is a quote from a computer art type, Harold Cohen from the University of California at San Diego: "For most people outside of art, probably, art is directed primarily at the production of beautiful objects and interesting images; and who is to argue that a complicated Lissajou figure is less beautiful than an Elsworth Kelly painting or a Jackson Pollock; or that a machine simulation of Mondrian is less interesting than the original it plagiarizes? To talk of beauty or of interest is to talk of taste, and matters of taste cannot be argued with much profit. The fact is that art is not, and never has been, concerned primarily with the making of beautiful or interesting patterns. The real power, the real magic, which remains still in the hands of the elite, rests not in the making of images, but in the conjuring of meaning." A little professorial, this. But do you think he has a point? Go back to your demonstration functions, the ones that have _no_ arguments so they do only _one_ thing. A function that does only one thing is like a box drawing function that draws only one size of box. One box doesn't encourage much thinking about the nature of boxes, does it? Can you use your demonstration functions to explore the nature of a collage that intrigues you? Play around with the collage demonstration function that draws it. Tinker a bit. Maybe you could generalize the demonstration function by adding an argument. To generalize a function is to stretch your thinking about what it does; and that's our appropriate work, too, because it respects the uniqueness of the Ludus art medium. "It's the tinkering that counts, not the artiness." Pin that phrase over your computer screen. ### Generalizing a function with arguments Let's go back to that `box!` function. Can we generalize it so that it draws triangle "boxes" as well as square ones? While we are at it, let's ask `box!` to draw boxes with any number of equal sides. These shapes will be regular polygons with n sides. Why not call the generalized function `ngon!` for n-sided polygon? Look again at the function BOX and decide what needs to be changed to turn `box!` into `ngon!`. ``` fn box! (edge) -> { repeat 4 { forward! (edge) right! (0.25) } } ``` You need to add a second argument `n`. This will tell Ludus how many sides to draw. We can replace the `repeat 4` with `repeat n`. `forward! (edge)` will stay the same, but what about the angle you want the turtle to turn before drawing the next side? It surely will be different for different sided polygons. Generally, sketching focuses geometric thinking. Here are some walking plans that you might issue to the turtle to do `ngon`s. {{Figure 5: Triangle, square, pentagon. Middle of p. 17.}} How can you calculate the angle indicated by the "?" for any n-sided polygon? Your geometric intuition should tell you that the turtle, after making `n` turns, will end up facing the same direction in which it started. The amount of each individual turn is simply a fraction of a whole turn, or `1/n`. Now is the time to understand Ludus's mathematical capacities. Consult the [Ludus documentation](https://alea.ludus.dev/twc/ludus/src/branch/main/prelude.md#math) for the functions to `add`, `sub`tract, `mult`iply, and `div`ide. > #### Angles in Ludus > Unlike high school geometry, Logo, or most other programming languages, Ludus measures its geometry in _turns_, rather than degrees or radians. > There are 360 degrees in a circle, and `2*pi` radians. > There is one single turn. > This is closer to lived geometry (turn a quarter turn to right, not 90 degrees). > It also simplifies much of the arithmetic here: we don't need to multiply or divide 360 or `2*pi` by anything. > > For example, Ludus has a very useful function named `inv`, which calculates the _inverse_ of its argument: `inv (n)` returns `1/n`. > So in this case, the angle to turn is simple `inv (n)`. > > #### Arithmetic in Ludus > Unlike many programming languages, Ludus does not have arithmetic operators. > In place of `2 + 2`, you will need to use the function `add`: `add (2, 2)`. > It will take some getting used to to read math expressed this way. > But it does offer a profound insight: nearly _everything_ in Ludus is a function call. > Addition isn't a special kind of thing. > > In addition, notice that while we have seen `forward!` and `right!` and `box!`, `add`'s name does not end in an exclamation point. > That is because, unlike a command, which makes something happen, it instead gives something back to you: the computed value. > Commands are actually special functions; `add` is a normal function. You are ready to write the new function `ngon!`: ``` fn ngon! (n, edge) -> { repeat n { forward! (edge) right! (inv (n)) } } ``` Try it out. Notice that when `n` becomes large, the drawn figure becomes a circle (almost). Carry out some clever visual experiments with `ngon`s. ### Some observations Look back carefully at what we have done so far with function writing. We started with a list of commands that drew a box of a single size. Next, we grouped these commands into functions that could draw boxes of several different sizes. Next, we generalized the `box!` function with an argument so that it could draw boxes of any size. Finally, we produced a still more general function, `ngon!`, that can draw any regular, polygonal "box"--triangles, squares, pentagons, hexagons, and so on--of whatever size we wanted. ### Making the simple more complete What next? How can we make these simple polygons more interesting? Maybe we can add another polygon characteristic to `ngon!`. Sometime in your life you were probably given an exercise like the following. "Cut out some different sized squares from a sheet of colored paper and think about placing the squares on a large piece of white paper. First, try to arrange the squares so that your design feels unbalanced and looks wonky. Next, rearrange the squares to create a balanced design." What kinds of changes did you make? What about creating an arrangement that looks sad and another that looks euphoric? Each design used the same squares. What made them different? Their placement. Make `ngon!` draw a bunch of `ngon`s and put them on the screen according to some placement rule. Take out your notebook and doodle. Here are some results from my doodling. Your approach will be different. I'll explain mine, and I'll expect that your plans will go into your notebook. Sketches of spinning polygons that grow or shrink as they spin {{Figure 6: Sketches of `box`es of different spins and sizes. Bottom of p. 19.}} ### Word description of sketched ideas "I want Ludus to draw a series of polygons rotating around a common point, and I want each successive polygon to get bigger, or maybe get smaller. "I don't know what angle to turn between one polygon and the next, so I'll include an argument called `angle` that I can vary, to see what happens. "I don't know how big the growth should be between one polygon and the next, so I'll define another argument called `growth`. I'll play with different values of `growth` to seewhat looks best. "How do I make `growth` work? Growth can be of two sorts: growth by a constant amount, or growth by a constant percentage. I'll try the latter. That means that if I want polygons to grow by 10%, I define `growth` to be 1.10. For a 90% shrinkage I would use `growth`=0.9." ### A function to spin polygons ``` fn spingon! (n, edge, angle, growth) -> { ngon! (n, edge) right! (angle) spingon! (n, mult (edge, growth), angle, growth) & Here is the recursion } ``` What is new here? First, there are more arguments than you have seen before. Every time you use `spingon!`, you must remember to type four numbers after it. Second, this function is recursive: the last line in the `spingon!` function asks that `spingon!` be done again, but with some arguments changed. For example, `edge` becomes `mult (edge, growth)` the first time recursion is called; and then `mult (edge, growth)` becomes `mult (mult (edge, growth), growth)` the second time recursion is called. A recursive function is a function that uses itself as one of its parts. Will `spingon!` ever stop? Try it out. > Then refresh the browser, since it will hang. ### Some spingons ``` spingon! (30, 2, inv (36), 1.02, 95) ``` {{Figure 7: Snail-ish spingon. Top of p. 21.}} ``` repeat! 3 { spingon! (4, 120, 0, 0.95, 50) right! (0.25) } spingon! (40, 120, 0, 0.25, 19) ``` {{Figure 8: Frame-ish spingons. Bottom of p. 21.}} ### Stopping recursive functions One last procedural writing point to review. Having put `spingon!` into motion, how do you make it stop at a stage of your choosing? You need to have a way of telling it how to stop. That's another characteristic to include as an argument. Look at the following modification to `spingon!`. Review the conditional commands in Ludus. `if ::something:: then ::something:: else ::something::` is such a conditional. Using the `if` form, everything becomes very tidy. ``` fn spingon! (n, edge, angle, growth, times) -> { & Note the new argument above. if lt? (times, 1) then :ok & This is the conditional stopper. else { ngon! (n, edge) rt! (angle) spingon! (n, mult (edge, growth), angle, growth, dec (times)) & Note the new argument above. } } ``` > `lt?` is the "less than" function. It is another kind of function: a predicate. Predicates return a boolean value, either `true` or `false`. Their names, by convention, end with a question mark. ### A note on the function presentation style used in this book I have tried to make the presentation of functions in this book as readable as possible. Here are several of my presentation rules. First, the _many comments_ rule. I have included wordy explanations in some of my functions. These comments begin with the Ludus comment character, `&`. There is, of course, no need for you to include thesecomments in your own version of my functions. However, it is a good idea for you to put comments in your own functions. Second, the _meaningful cluster_ rule. I often include extra parentheses to group like elements into a cluster. This is useful, for example, when an argument is composed of a collection of Ludus material, but you want to see it as a single cluster of information. Here is an example from this chapter. Notice the use of comments, too. ``` fn spingon! (n, edge, angle, growth, times) -> { & Note the new argument above. if lt? (times, 1) then :ok & This is the conditional stopper. else { ngon! (n, edge) rt! (angle) spingon! (n, mult (edge, growht), angle, growht, dec (times)) & Note the new argument above. } } ``` Third, the _body structuring_ rule. Functions should be laid out nicely in the editor without too much information on any one line. Long function statements should be divided up between lines to make them more readable. Code blocks--those curly braces that group lines of code together--should always come with an increase in how indented lines are. ### Exercises There are five exercises to explore before going on to the material of chapter 2. The first is so important that we will go through it together, step by step. You can work on the other exercisesby yourself. #### Exercise 1.1 Make `ngon!` more versatile by doing two things to it. First, improve `ngon!` so that it will draw polygons _around a central point_; and second, improve `ngon!` so that it can be given an argument that specifies not the length of an edge of the polygon but the _radius of the polygon_. I've made up the term radius of a polygon. It is the radius of the smallest circle that just encloses a regular polygon. The center of this circle is the point around which the polygon is to be drawn. Seethe diagram below. {{Figure 9: Polygons inscribed in dotted circles. Bottom of p. 24}} Call the revised function `cngon!` for "**c**entered **NGON**." Two hints: First, ask yourself what arguments `cngon!` will need. This is another way to ask yourself what information must be given to `cngon!` so that it can go about its business of drawing centered `ngon`s. `cngon!` needs only two pieces of information, or two arguments: the number of sides of the polygon to be drawn and the radius of that polygon. That means that the first line of the new function will look like this: ``` cngon! (n, radius) ``` Second, imagine yourself as the turtle. How would you walk through the design that `cngon!` must make? Draw a simple diagram to describe such a "turtle walk." You might want to divide the diagram up into individual scenes. Later you can translate each scene in words and then into Ludus notation. Here is the first instance where this turtle visualization is really needed. Let yourself go; talk out loud; get on with it without too much thinking. ### Word description of the turtle walk (see sketches on next page) Diagram A: **Getting ready to draw the polygon**. You, as the turtle, begin your journey from position (1), the center of the proposed polygon. You are facing straight up. Pick up your pen and move forward by the amount of the polygon's radius. This is `radius`. This puts you in position (2). You now need to turn right by an amount that is labeled (angle) on the sketch (3). What will (angle) be related to? Will (angle) be different for differently shaped polygons, that is, polygons with different numbers of sides? Yes. Will (angle) be related to the overall size of polygons? No. Don't worry about how to calculate (angle), yet; you can work that out later. ### Turtle walk sketches {{Figure 10: Turtle walk sketches. p. 26.}} After turning right by the amount of (angle), you are looking along one of the polygon's edges (4). Put down the pen in preparation for drawing the polygon. Diagram B: **Drawing the polygon**. You are at position (4) and ready to draw an n-sided polygon. You can use the function `ngon!`. But what arguments will you use? It needs some values for `n` and `edge`. Right? Yes, but wait a minute. What should the value for `edge` be? You know the value of `n`, the number of sides of the polygon. And you know the value of the new argument, `radius`. What must the polygon's edge dimension be so that, after it is drawn, it has a radius equal to `radius`? In other words, we need to be able to express `edge` in terms of `n` and `radius`. OK. We know the problem, what we have to work on, but let's not stop yet. Label the edge thing that must be calculated (edge). We will return to it in a minute. Now you can draw an `ngon! (n, edge)`. You began the `ngon` from position (4). You will end at the same place. Diagram C: **Getting ready to return to the center**. You are at position (6). You must now turn left by the amount of (angle); this is indicated by (7). This leaves you in position (8), pointing straight up. Diagram D: **Returning to the center of the polygon**. Pick up your pen and back down, by an amount equal to `radius`, to the polygon's center. Finally, put your pen down in preparationfor whatevermight comenext. Note that you, as the turtle, have ended in the sameposition (9) as you began (1). ### A turtle walk transfonned into a Ludus function (almost) No more words are necessary. Here it is. ``` fn cngon! (n, radius) -> { penup! () forward! (radius) right! (angle) pendown! () ngon! (n, edge) left! (angle) penup! () back! (radius) pendown! () } ``` The function is sketched. And we know what we know and what we don't. The two amounts, `angle` and `edge`, are still unknown. To figure these bits will require a little geometry and trigonometry. We might as well use this opportunity to review all the bits and pieces of polygons. ### The Geometry of CNGONs Use the following two diagrams in conjunction with the word and equation descriptions. {{Figure 11: Geometry of `cngon`s. Bottom of p. 28.}} The first problem we face is to find an expression for angle `d` in terms of `n`, the number of sides of the polygon. The second problem is to find an expression for the length of a polygon's edge, `e`, in terms of its radius, `R`, and `n`, the number of sides. In preparation for these two acts, let's look at all the angles associated with polygons. The _central angles_, labeled a, are easy. They are each equal to 1/n (or `inv (n)`). The _external angles_, labeled `c`, are also equal to 1/n. The external angle is the turning angle used in `ngon!`. What about the internal angles, labeled `b`. We need some work here: ``` (1) c = 1/n, (2) c + b = 1/2. ``` Putting these two equations together and solving for `b` gives ``` (3) b = 1/2 - 1/n. ``` We are now ready to handle the first problem: Find `d` in terms of `n`. ``` (4) d + b/2 = 1/2. ``` Putting (3) and (4) together and solving for d gives ``` (5) d = 1/4 + 1/2n <-- First problem solved. ``` OK, now look at the second problem: Find e in terms of R and n. ``` (6) sin (a/2) = (e/2)/R, (7) a = 1/n. ``` Putting (7) and (6) togetherand solving for e gives ``` (8) e = 2*R*sin(1/2n) <-- Second problem solved. ``` Review the following trig functions: sine, cosine, and tangent. What is ani arctangent? Draw some diagrams to explain each of these functions. Glue them on the inside cover of your notebook. ### Installing the necessary geometry into `cngon!` Here's how far we have gotten with `cngon!`: ``` fn cngon! (n, rad) -> { penup! () forward! (rad) right! (angle) pendown! () ngon! (n, edge) left! (angle) penup! () back! (rad) pendown! () } ``` Now we can use `let` bindings to give `angle` and `edge` with the needed values, by translating our equations into Ludus code. Here is the finished `cngon!`: ``` fn cngon! (n, radius) -> { let angle = sub (inv (2), inv (n)) let edge = mult (2, radius, sin (inv (mult (2, n)))) penup! () forward! (radius) right! (angle) pendown! () ngon! (n, edge) left! (angle) penup! () back! (radius) pendown! () } ``` ### Lessons and tips When solving visual problems, like this `cngon!` thing, try to break the single big problem down into several smaller problems. Solve each of the small problems in turn, and then plug the little solutions together to form one big solution. #### Exercise 1.2 Put together one or more `demo!` functions that make imaginative use of the ideas presented and reviewed in this chapter. Modify every function in the chapter. Make them act more strangely. You might want to think some more about the exercise, described above, of placing simple shapes on a blank field of paper to depict different feelings of balance or emotions. A painting by the Russian artist Kasimir Malevich is reproduced below. What could be more elegant that these eight red rectangles? (That' s the title, by the way.) What emotion do you feel when looking at this littel reproduction? Can you do something similar? {{Figure 12: Kasimir Malevich, _Eight Red Rectangles_. https://upload.wikimedia.org/wikipedia/commons/thumb/6/6d/Malevich-Suprematism..jpg/640px-Malevich-Suprematism..jpg. Bottom of p. 31.}} #### Exercise 1.3 Combine the ideas of `spingon!` with your newly constructed `cngon!`. ### Exercise 1.4 Design a fancier `cngon!` that fills up a polygon with textures. Here are a few visual tips for Exercises 1.3 and 1.4: {{Figure 13: `spincngon`s. Bottom of p. 32.}} #### Exercise 1.5 Design a Ludus function that puts polygons on the vertices of other polygons. Hint: look carefully at the body of `cngon!`. When does the turtle arrive at a polygon vertex? Mark the vertex arrival place in the `cngon!` function. You might consider this location as the right spot to install some recursion: when the turtle arrives at any vertex, ask it to do another `cngon!` centered on that vertex. This recursive drawing will place polygons on the vertices of polygons on the vertices of polygons. You will need to figure out a way of stopping the recursion machinery, or it will continue forever. Define a new argument, `level`, to keep track of recursion levels. What about the relative sizes of the polygons? Should they get bigger or smaller? Can you handle that? Don't forget the following tricks: 1. Imagine yourself as the turtle. 2. Sketch the design that the turtle must walk through. 3. Describe the turtle walk in words. 4. Divide the walk up into logical sections. 5. Note the bits you know and the bits that will need some further thought and research. 6. Translate the words into Ludus commands. 7. Test it out with realistic and totally outlandish argument values ### Notes for adaptation * A few places there are arbitrary degrees; figure out how to make this friendlier. * The canvas doesn't (currently) wrap, so the example of many squares with wrapping needs to be a bit different. * Prepping the annotated SVGs will be a thing. - Do we want hand-drawn stuff? Consider using the iPad. * Things we do need that are absent (in no particular order): - M-expression math - A discussion of empty parens/function calls