Rätselkoffer programmieren

Ich habe hier schon schon einmal das Spiel „Keep Talking and Nobody Explodes“ vorgestellt. Ein Spieler oder eine Spielerin sitzt dabei am Rechner vor einem virtuellen Bombenkoffer, den es zu entschärfen gilt, und zwar alle drei (oder mehr) Module am Koffer. Eines davon ist das Drahtdurchschneiden, das man aus Filmen kennt: Es gibt eine Reihe von farbigen Drähten, die man in bestimmter Reihenfolge durchschneiden muss. Nur welche Reihenfolge?

Die anderen Spieler und Spielerinnen, und nur die, haben alle das hochkomplizierte Bombenentschärf-Handbuch vor sich liegen, sehen aber nicht den Bombenkoffer. Also muss man miteinander reden – es ist ein Dialogspiel: Wie viele Drähte? Welche Farben haben sie? Welche anderen Merkmale gibt es an dem Modul oder am ganzen Koffer? Davon hängt dann die Lösung ab.

So etwas habe ich in grob vereinfachter Form für meine Informatikklasse programmiert. Allerdings habe ich das ganze „Rätselkoffer“ genannt – das gibt mehr Spielraum für die verschiedenen Module und ist nicht ganz so gewalttätig.

Das Drahtdurchschneide-Grafikmodul sieht zum Beispiel so aus (eigentlich nur der gelb hinterlegte Bereich):

Das sind einfach sieben recht schmale und hohe Knöpfe oben und ein paar Ausgabefelder unten. Für die Knöpfe gibt es Methoden, um eine beliebige Grafik als Hintergrund zu setzen, und vorgefertigt sind Grafiken mit Drähten in verschiedenen Farben, durchgeschnitten oder ganz.

Eine andere Modul-Grafik (ein Schülerwunsch) sieht so aus: Drei quadratische Knöpfe oben, ein breiter, niedrigerer Knopf darunter. Die Knöpfe oben kann man zum Beispiel mit solchen Bildern füllen:

Was man mit den Knöpfen beziehungsweise dem ganzen grafischen Block macht, bleibt den Schülern und Schülerinnen überlassen. Tatsächlich besteht jedes Rätselmodul aus zwei Objekten, die in den Klassen ModulGUI und Modul beziehungsweise Unterklassen davon beschrieben werden: ModulGUI ist lediglich die Grafik des aktuellen Elements; die Unterklassen dazu stelle ich zur Verfügung. (Denn Grafikprogrammierung in Java ist einfach zu fisselig, wenn man sie noch nie gemacht hat, auch wenn die Elemente ja nur aus verschieden großen Buttons und Ein- und Ausgabeflächen bestehen.) Zu jedem ModulGUI-Objekt gehört ein Modul-Objekt, das die Spiellogik und Steuerung übernimmt. Und eben dieses (beziehungsweise die Unterklassen dazu) wird von den Schülern und Schülerinnen programmiert: Im Beispiel ist das die Klasse Demo:

Die Demo-Klasse legt erstens ein WireGUI-Objekt an, um diesem Nachrichten zu schicken, wie welcher Knopf aussehen soll. Und zweitens macht sie sich zur Unterklasse von Modul, damit das WireGUI-Objekt seinerseits Nachrichten – darüber, welche Knöpfe gedrückt werden – an das Demo-Objekt, also die Steuerung, schicken kann.

So sieht eine zu programmierende Klasse dann aus:

public class Demo extends Modul 
{
    WireGUI gui;
 
    public Demo() {
        gui = new WireGUI();
        gui.setSteuerung(this);
        gui.setButtonImage(1, "drahtRot.png");
    }
 
    @Override
    public WireGUI getGUI() { 
        return gui; 
    }
 
    @Override
    public void empfangeKnopfdruck(int knopfnr) {
        if (knopfnr==1) { gui.setButtonImage(1, "drahtRotCut.png"); }
    }
}

So sieht das alles in BlueJ aus:

An der linken Seite sieht man einige mögliche Grafik-Unterklassen. An der unteren Seite sind die Steuerung-Unterklassen, also die von den Schülern und Schülerinnen zu programmierenden. Das obere Drittel ist technischer Kram, ausgebreitet auf verschiedene Klasse zur leichteren Wartung.

Könnte man in sie hineinblicken, wirkten sie vielleicht ein wenig umständlich, und das liegt daran, dass die Grafikbibliothek JavaFX und BlueJ nicht optimal zusammenarbeiten. Wenn ich Objekte in der Objektleiste unten haben und ansprechen können möchte, muss ich tricksen. (Der JavaFX-Thread lässt sich nicht gerne von außen unterbrechen, will heißen: durch manuelle Methodenaufrufe von BlueJ aus.) Und so gibt es mehre Möglichkeiten, etwas zu sehen zu kriegen:

  • in der Main-Klasse die statische Methode launch(String[] args) aufrufen, die den JavaFX-Thread startet
  • ein Main-Objekt anlegen oder eine andere statische Methode darin aufrufen, dann wird die JavaFX-Grafik gekapselt in einem JavaSwing-JFrame und ist damit für Objekte in der Objektbank zugänglich (tatsächlich gibt es noch einen Schönheitsfehler dabei, anderes Thema)
  • ein Objekt einer Modul-Unterklasse anlegen, das sich eine ModulGUI-erzeugt, das letztlich die JFrame-Methode der Main-Klasse aufruft (Vorteil: man kann die Methode der Klasse manuell aufrufen und testen, wenn sie den JavaFX-Thread beeinflussen, muss man aber Umstände machen)
  • ein Objekt einer ModulGUI-Unterklasse anlegen, das sich eine Dummy-Steuerung gibt, die letztlich die JFrame-Methode der Main-Klasse aufruft (Vorteil: wie oben) – Ziel dieser letzten beiden Konstruktionen: Die Schüler und Schülerinnen sollen einfach wie gewohnt Objekte ihrer Klassen erzeugen können, deren Oberklassen sich dann darum kümmern, dass Grafik hergestellt wird

JavaFX bietet einige grafische Elemente, mit denen man so ein Rätselmodul aufpeppen kann. Man kann sie auch alle leicht vergrößern, verkleinen, drehen, sich bewegen lassen:

Das Projekt befindet sich noch in einem Rohstadium. Ich weiß noch nicht, wie ich die einzelnen Module am besten zusammenfügen soll. Soll das Spiel aus sein, wenn man ein Modul vergeigt? Oder wird das dann einfach beendet und gesperrt und man kriegt Punktabzug? Soll es einen globalen Timer geben? Vorläufig habe ich ein Modul als Startseite, über das man auf andere, zufällig ausgewählte Module gelangt, von denen aus kann man zurück, wenn man das will:

Einsatz in der Schule: Mir gefällt die Idee, dass jedes Programmierteam ein Modul erarbeitet, die danach zu einem Spiel zusammengetragen werden. Viel müssen die Schüler und Schülerinnen eigentlich nicht können: Ein Objekt erzeugen und in einem Attribut speichern, Methoden des Objekts aufrufen, eine Unterklasse anlegen, eine Methode implementieren void empfangeKnopfdruck(int knopfnummer) – und vermutlich bedingte Anweisungen, um das sinnvoll machen zu können. Trotzdem war ich zu früh dran mit dem Ausprobieren mit meiner Klasse; das erfordert halt doch mehr Abstraktionsvermögen und Programmiererfahrung, als man meint. Inzwischen hat die Klasse einfache Zustandsautomaten programmiert und ist mit if und if else vertrauter; vielleicht komme ich noch einmal darauf zurück. Die JavaFX-Grafikklassen erstelle ich übrigens mit dem Java-Editor, sie erfordern dann nur wenig Anpassung, um sie zu ModulGUI-Unterklassen machen zu können. Der Auftrag dazu für die Schüler und Schülerinnen: Erstelle eine Skizze, wie die (quadratische) Grafikoberfläche für dein Modul aussehen soll, welche Knöpfe oder Felder du darin gerne hättest, und welche Methoden dir das Objekt zur Verfügung stellen soll, damit du die Oberfläche auf die gewünschte Weise verändern kannst.

(Hilfsmethoden, die die Klasse Modul zur Verfügung stellt: Abspielen von mp3-Dateien, Erzeugen von Tönen, Verzögertes Ausführen einer Methode, Countdown.)

– In den Sommerferien komme ich hoffentlich endlich mal dazu, meine ganzen Programmierprojekte für die 10. Jahrgangsstufe ordentlich bei github oder so einzustellen und in einem Mebiskurs zu präsentieren.

4 Antworten auf „Rätselkoffer programmieren“

  1. Mich hat Keep Talking and Nobody Explodes auch inspieriert, allerdings in die andere Richtung: Ich habe es als Hardware nachgebaut.
    Das Ding ist ebenfalls modular aufgebaut, mit dem gleichen Hintergedanken, dass Schüler einer Klasse oder Teilnehmer eines Workshops einzelne Module löten (und ggf. programmieren) können, die dann zu einem großen Ganzen zusammengesteckt werden. Außerdem kann sich so das Spiel immer wieder verändern oder in der Schwierigkeit angepasst werden. Ein paar Bilder findet man auf der Homepage des Projekts: tetopia.de/programmieren/bombe

  2. Ist das cool! Also, quasi, endcool. Sagenhaft! (Das darf ich doch bei Twitter herumerzählen, hoffe ich?) Ich kenne ja schon so Escape-Room-Koffer, auch gerne mal für die Schule entworfen, habe aber nie damit gearbeitet – diese bestehen aber aus klassischen Rätseln und Schlössern und nichts sehr Elektrischem.

  3. Natürlich darf das bei twitter auftauchen, ich fühle mich geehrt :-)
    Apropos Hardware: Ich habe auch „Krümel und Monster“ in Hardware umgesetzt. Das Spiel hat für mich sentimental value, weil ich damit meine Liebe fürs Programmieren entdeckt habe. Findet sich bei mir auf der Homepage unter „Arduino“, bzw. auf dem dort verlinkten Git-Hub-Repo.

  4. Danke, ist auch schön. (Bei Twitter ist die erwartete Sensation ausgeblieben. Also ich find’s immer noch sensationell, auch wenn ich gar kein Bastler bin.) Krümel hat lange nicht funktioniert, weil für zu alte Java-Version angelegt, ich hab’s inzwischen angepasst, so dass es wieder funktioniert, aber nicht mehr in der Schule ausprobiert. Kann mich aber noch gut erinnern.

Schreibe einen Kommentar

Deine E-Mail-Adresse wird nicht veröffentlicht. Erforderliche Felder sind mit * markiert.