Das Turtle Teachpack

Einleitung

Turtle-Grafik ist eine Methode zum Erstellen von Computergrafiken. Das Zeichnen wird dabei durch das Bewegen einer virtuellen Schildkröte über den Zeichenbereich modelliert. Eine Schildkröte kann durch drei Befehle bewegt werden:

Wir stellen jetzt ein Teachpack für DrScheme vor, mit dessen Hilfe solche Turtle-Grafiken erstellt werden können.

Installation

Sie können das Teackpack installieren, indem Sie im Menü Sprache den Befehl Teachpack hinzufügen wählen. Dann müssen Sie die Datei turtle.ss den selbst installierte Teachpacks hinzufügen.

Tutorial

Unser Ziel ist es, in diesem Tutorial ein Quadrat mithilfe der Funktionen des Teachpacks zu zeichnen. Aus diesem Grund müssen wir zunächst mit der Prozedur draw eine Linie nach rechts malen. Die initiale Ausgansposition der Turtle ist in der Bildmitte mit Blick nach rechts. Mit (draw 20) bewegen wir die Turtle dann 20 Pixel nach rechts und zeichnen dabei. Um das resultierende Bild zu sehen ist, müssen wir die Turtle mittels der Funktion run laufen lassen. Die restlichen Parameter für run sind die Höhe und die Breite des Bildes sowie die Farbe, in der gezeichnet werden soll. Geben Sie also folgenden Befehl in die REPL ein, um Ihre erste Turtle-Grafik zu erstellen:

(run (draw 20) 100 100 "red")

Sie erhalten dann eine Ausgabe wie die folgende:

Nun vervollständigen wir die Linie zu einem rechten Winkel: wir drehen die Turtle um 90° nach rechts und zeichnen dann eine Line der Länge 20 Pixel nach unten. Zum Drehen einer Turtle verwenden wir die Funktion turn.

Da wir ein Quadrat aus zwei rechten Winkeln zusammensetzen können, abstrahieren wir über das Zeichnen des rechten Winkels. Dazu schreiben wir eine Prozedur right-angle die als Parameter eine Turtle erhält:

; right-angle : turtle -> turtle
(define right-angle 
  (lambda (t1)
    (let* ((t2 ((draw 20) t1))
           (t3 ((turn -90) t2))
           (t4 ((draw 20) t3)))
      t4)))

Das Ergebnis sieht dann so aus:

Um das Quadrat komplett zu zeichnen, sollen nun zwei rechte Winkel verwendet werden. Wir zeichnen also einen rechten Winkel, drehen uns um 90° nach rechts, und zeichnen einen zweiten rechten Winkel.

; square : turtle -> turtle
(define square  
  (lambda (t1)
    (let* ((t2 (right-angle t1))
           (t3 ((turn -90) t2))
           (t4 (right-angle t3)))
      t4)))

So sieht das Ergebnis aus:

Verbesserungen

An dem Beispiel ist leicht zu sehen, dass es zum Zeichnen mit Hilfe von Turtle-Grafik oft erforderlich ist, Zwischenwerte wie t1, t2 etc., an die nächste Funktion weiterzureichen, die Werte ansonsten aber nicht weiterverwendet werden. Beispielsweise werden in der obigen Definition von square die Variablen t1, ..., t4 nur gebraucht, um die Prozeduren right-angle, (turn -90) und right-angle hintereinander auszuführen.

Um solche Fälle einfach programmieren zu können, enthält das Turtle Teachpack die Prozedur sequence. Damit können wir eine zu right-angle äquivalente Version wesentlicher einfacher aufschreiben:

(define right-angle2 
  (sequence (draw 20) (turn -90) (draw 20)))
Ebenso wie right-angle können wir square leichter schreiben als:

(define square2  
  (sequence right-angle (turn -90) right-angle))

Funktionen

Funktionen, die das Teachpack bereitstellt:

set-color

Diese Funktion ist eine Funktionsfabrik. Sie liefert als Ergebnis eine Funktion, die auf eine turtle anwendbar ist. Wendet man das Ergebnis auf eine turtle an, so ändert dies die Farbe mit der gezeichnet wird.

set-color: color -> (turtle -> turtle) 

Beispiel

Folgender Code

(define square3
  (sequence right-angle (turn -90) (set-color "blue") right-angle))

liefert dieses Bild:

turn

Diese Funktion ist eine Funktionsfabrik. Sie liefert als Ergebnis eine Funktion, die auf eine turtle anwendbar ist. Wendet man das Ergebnis auf eine turtle an, so ändert sich die Blickrichtung der Turtle um die gegebene Gradzahl gegen den Uhrzeigersinn.

turn: number -> (turtle -> turtle) 

draw

Diese Funktion ist eine Funktionsfabrik. Sie liefert als Ergebnis eine Funktion, die auf eine turtle anwendbar ist. Wendet man das Ergebnis auf eine turtle an, so bewegt sich die Schildkröte um die gegebene Anzahl von Pixel und zeichnet dabei eine Linie.

draw: number -> (turtle -> turtle) 

move

Diese Funktion ist eine Funktionsfabrik. Sie liefert als Ergebnis eine Funktion, die auf ein turtle anwendbar ist. Wendet man das Ergebnis auf eine turtle an, so bewegt sich die Schildkröte um die gegebene Anzahl von Pixel, zeichnet dabei aber keine Linie.

draw: number -> (turtle -> turtle) 

run

Diese Funktion wendet die übergebene Funktion von turtle nach turtle auf die initiale Schildkröte an und zeigt das daraus resultierende Bild an. Der zweite Parameter ist die Höhe des Bilds, der dritte Parameter die Breite des Bilds und der vierte Parameter die Farbe, mit der gezeichnet wird.

run: (turtle -> turtle) number number color -> image

sequence

Diese Funktion nimmt eine beliebige Anzahl von Turtle-Veränderungen (d.h. Funktionen mit Typ turtle -> turtle) und erstellt eine neue Funktion, die die Veränderungen der Reihe nach von links nach rechts abarbeitet.

sequence: (turtle -> turtle) ... -> (turtle -> turtle)

Last modified: Fri Dec 7 07:53:05 CET 2007